<!DOCTYPE html><html lang="zh-CN" data-theme="dark"><head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width,initial-scale=1"><title>数据类型函数 | 北城韩雨</title><meta name="keywords" content="JS高级"><meta name="author" content="北城韩雨"><meta name="copyright" content="北城韩雨"><meta name="format-detection" content="telephone=no"><meta name="theme-color" content="#0d0d0d"><meta name="description" content="JS高级">
<meta property="og:type" content="article">
<meta property="og:title" content="数据类型函数">
<meta property="og:url" content="http://example.com/2019/03/31/%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E5%87%BD%E6%95%B0/index.html">
<meta property="og:site_name" content="北城韩雨">
<meta property="og:description" content="JS高级">
<meta property="og:locale" content="zh_CN">
<meta property="og:image" content="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-12-05%2F66b696ea615f3567a32b65f93611a814%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&refer=http%3A%2F%2Fpic.vjshi.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530687&t=c2e3c97de6dbdc29e77593d5f4dc7fb5">
<meta property="article:published_time" content="2019-03-30T16:00:00.000Z">
<meta property="article:modified_time" content="2019-06-02T16:00:00.000Z">
<meta property="article:author" content="北城韩雨">
<meta property="article:tag" content="JavaScript">
<meta name="twitter:card" content="summary">
<meta name="twitter:image" content="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-12-05%2F66b696ea615f3567a32b65f93611a814%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&refer=http%3A%2F%2Fpic.vjshi.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530687&t=c2e3c97de6dbdc29e77593d5f4dc7fb5"><link rel="shortcut icon" href="/img/favicon.png"><link rel="canonical" href="http://example.com/2019/03/31/%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E5%87%BD%E6%95%B0/"><link rel="preconnect" href="//cdn.jsdelivr.net"/><link rel="preconnect" href="//busuanzi.ibruce.info"/><link rel="stylesheet" href="/css/index.css"><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@fortawesome/fontawesome-free/css/all.min.css" media="print" onload="this.media='all'"><script>const GLOBAL_CONFIG = { 
  root: '/',
  algolia: undefined,
  localSearch: undefined,
  translate: undefined,
  noticeOutdate: undefined,
  highlight: {"plugin":"highlighjs","highlightCopy":true,"highlightLang":true,"highlightHeightLimit":false},
  copy: {
    success: '复制成功',
    error: '复制错误',
    noSupport: '浏览器不支持'
  },
  relativeDate: {
    homepage: false,
    post: false
  },
  runtime: '',
  date_suffix: {
    just: '刚刚',
    min: '分钟前',
    hour: '小时前',
    day: '天前',
    month: '个月前'
  },
  copyright: undefined,
  lightbox: 'mediumZoom',
  Snackbar: undefined,
  source: {
    jQuery: 'https://cdn.jsdelivr.net/npm/jquery@latest/dist/jquery.min.js',
    justifiedGallery: {
      js: 'https://cdn.jsdelivr.net/npm/justifiedGallery/dist/js/jquery.justifiedGallery.min.js',
      css: 'https://cdn.jsdelivr.net/npm/justifiedGallery/dist/css/justifiedGallery.min.css'
    },
    fancybox: {
      js: 'https://cdn.jsdelivr.net/npm/@fancyapps/fancybox@latest/dist/jquery.fancybox.min.js',
      css: 'https://cdn.jsdelivr.net/npm/@fancyapps/fancybox@latest/dist/jquery.fancybox.min.css'
    }
  },
  isPhotoFigcaption: false,
  islazyload: false,
  isanchor: false
}</script><script id="config-diff">var GLOBAL_CONFIG_SITE = {
  title: '数据类型函数',
  isPost: true,
  isHome: false,
  isHighlightShrink: false,
  isToc: true,
  postUpdate: '2019-06-03 00:00:00'
}</script><noscript><style type="text/css">
  #nav {
    opacity: 1
  }
  .justified-gallery img {
    opacity: 1
  }

  #recent-posts time,
  #post-meta time {
    display: inline !important
  }
</style></noscript><script>(win=>{
    win.saveToLocal = {
      set: function setWithExpiry(key, value, ttl) {
        if (ttl === 0) return
        const now = new Date()
        const expiryDay = ttl * 86400000
        const item = {
          value: value,
          expiry: now.getTime() + expiryDay,
        }
        localStorage.setItem(key, JSON.stringify(item))
      },

      get: function getWithExpiry(key) {
        const itemStr = localStorage.getItem(key)

        if (!itemStr) {
          return undefined
        }
        const item = JSON.parse(itemStr)
        const now = new Date()

        if (now.getTime() > item.expiry) {
          localStorage.removeItem(key)
          return undefined
        }
        return item.value
      }
    }
  
    win.getScript = url => new Promise((resolve, reject) => {
      const script = document.createElement('script')
      script.src = url
      script.async = true
      script.onerror = reject
      script.onload = script.onreadystatechange = function() {
        const loadState = this.readyState
        if (loadState && loadState !== 'loaded' && loadState !== 'complete') return
        script.onload = script.onreadystatechange = null
        resolve()
      }
      document.head.appendChild(script)
    })
  
      win.activateDarkMode = function () {
        document.documentElement.setAttribute('data-theme', 'dark')
        if (document.querySelector('meta[name="theme-color"]') !== null) {
          document.querySelector('meta[name="theme-color"]').setAttribute('content', '#0d0d0d')
        }
      }
      win.activateLightMode = function () {
        document.documentElement.setAttribute('data-theme', 'light')
        if (document.querySelector('meta[name="theme-color"]') !== null) {
          document.querySelector('meta[name="theme-color"]').setAttribute('content', '#ffffff')
        }
      }
      const t = saveToLocal.get('theme')
    
          if (t === 'dark') activateDarkMode()
          else if (t === 'light') activateLightMode()
        
    const detectApple = () => {
      if (GLOBAL_CONFIG_SITE.isHome && /iPad|iPhone|iPod|Macintosh/.test(navigator.userAgent)){
        document.documentElement.classList.add('apple')
      }
    }
    detectApple()
    })(window)</script><link rel="stylesheet" href="/css/custom.css"  media="defer" onload="this.media='all'"><link rel="stylesheet" href="/css/coin.css"  media="defer" onload="this.media='all'"><link rel="stylesheet" href="/css/liuxing.css"><link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/l-lin/font-awesome-animation/dist/font-awesome-animation.min.css"  media="defer" onload="this.media='all'"><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/swiper/swiper-bundle.min.css"><link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/zhheo/JS-Heo@main/bb/showbb_in_index.css"><!-- hexo injector head_end start --><link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/4.1.1/animate.min.css" media="print" onload="this.media='screen'"><link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/l-lin/font-awesome-animation/dist/font-awesome-animation.min.css" media="defer" onload="this.media='all'"><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/hexo-butterfly-tag-plugins-plus/lib/tag_plugins.min.css" media="defer" onload="this.media='all'"><!-- hexo injector head_end end --><meta name="generator" content="Hexo 5.3.0"></head><body><div id="web_bg"></div><div id="sidebar"><div id="menu-mask"></div><div id="sidebar-menus"><div class="avatar-img is-center"><img src="/img/my.jpg" onerror="onerror=null;src='/img/friend_404.gif'" alt="avatar"/></div><div class="site-data"><div class="data-item is-center"><div class="data-item-link"><a href="/archives/"><div class="headline">文章</div><div class="length-num">65</div></a></div></div><div class="data-item is-center"><div class="data-item-link"><a href="/tags/"><div class="headline">标签</div><div class="length-num">23</div></a></div></div><div class="data-item is-center"><div class="data-item-link"><a href="/categories/"><div class="headline">分类</div><div class="length-num">21</div></a></div></div></div><hr/><div class="menus_items"><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/"><i class="fa-fw fas fa-home faa-tada"></i><span> 首页</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/shuoshuo/"><i class="fa-fw fas fa-archive faa-tada"></i><span> 叨逼叨</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/tags/"><i class="fa-fw fas fa-tags faa-tada"></i><span> 标签</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/categories/"><i class="fa-fw fas fa-folder-open faa-tada"></i><span> 分类</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/link/"><i class="fa-fw fas fa-link faa-tada"></i><span> 友链</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/comments/"><svg class="icon faa-tada" aria-hidden="true"><use xlink:href="#icon-message"></use></svg><span> 留言板</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/about/"><i class="fa-fw fas fa-heart faa-tada"></i><span> 个人简介</span></a></div></div></div></div><div class="post" id="body-wrap"><header class="post-bg" id="page-header" style="background-image: url('https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-12-05%2F66b696ea615f3567a32b65f93611a814%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&amp;refer=http%3A%2F%2Fpic.vjshi.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530687&amp;t=c2e3c97de6dbdc29e77593d5f4dc7fb5')"><nav id="nav"><span id="blog_name"><a id="site-name" href="/">北城韩雨</a></span><div id="menus"><div class="menus_items"><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/"><i class="fa-fw fas fa-home faa-tada"></i><span> 首页</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/shuoshuo/"><i class="fa-fw fas fa-archive faa-tada"></i><span> 叨逼叨</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/tags/"><i class="fa-fw fas fa-tags faa-tada"></i><span> 标签</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/categories/"><i class="fa-fw fas fa-folder-open faa-tada"></i><span> 分类</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/link/"><i class="fa-fw fas fa-link faa-tada"></i><span> 友链</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/comments/"><svg class="icon faa-tada" aria-hidden="true"><use xlink:href="#icon-message"></use></svg><span> 留言板</span></a></div><div class="menus_item"><a class="site-page faa-parent animated-hover" href="/about/"><i class="fa-fw fas fa-heart faa-tada"></i><span> 个人简介</span></a></div></div><div id="toggle-menu"><a class="site-page"><i class="fas fa-bars fa-fw"></i></a></div></div></nav><div id="post-info"><h1 class="post-title">数据类型函数</h1><div id="post-meta"><div class="meta-firstline"><span class="post-meta-date"><i class="far fa-calendar-alt fa-fw post-meta-icon"></i><span class="post-meta-label">发表于</span><time class="post-meta-date-created" datetime="2019-03-30T16:00:00.000Z" title="发表于 2019-03-31 00:00:00">2019-03-31</time><span class="post-meta-separator">|</span><i class="fas fa-history fa-fw post-meta-icon"></i><span class="post-meta-label">更新于</span><time class="post-meta-date-updated" datetime="2019-06-02T16:00:00.000Z" title="更新于 2019-06-03 00:00:00">2019-06-03</time></span><span class="post-meta-categories"><span class="post-meta-separator">|</span><i class="fas fa-inbox fa-fw post-meta-icon"></i><a class="post-meta-categories" href="/categories/JS%E9%AB%98%E7%BA%A7/">JS高级</a></span></div><div class="meta-secondline"><span class="post-meta-separator">|</span><span class="post-meta-wordcount"><i class="far fa-file-word fa-fw post-meta-icon"></i><span class="post-meta-label">字数总计:</span><span class="word-count">9.3k</span><span class="post-meta-separator">|</span><i class="far fa-clock fa-fw post-meta-icon"></i><span class="post-meta-label">阅读时长:</span><span>33分钟</span></span><span class="post-meta-separator">|</span><span class="post-meta-pv-cv" id="" data-flag-title="数据类型函数"><i class="far fa-eye fa-fw post-meta-icon"></i><span class="post-meta-label">阅读量:</span><span id="busuanzi_value_page_pv"></span></span></div></div></div></header><main class="layout" id="content-inner"><div id="post"><article class="post-content" id="article-container"><h2 id="数据类型"><a href="#数据类型" class="headerlink" title="数据类型"></a>数据类型</h2><h3 id="基本数据类型-原始值类型"><a href="#基本数据类型-原始值类型" class="headerlink" title="基本数据类型(原始值类型)"></a>基本数据类型(原始值类型)</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> number -&gt; <span class="literal">NaN</span>/<span class="literal">Infinity</span></span><br><span class="line"><span class="number">2.</span> string -&gt; 单引号/双引号/反引号</span><br><span class="line"><span class="number">3.</span> boolean -&gt; <span class="literal">true</span> / <span class="literal">false</span></span><br><span class="line"><span class="number">4.</span> <span class="literal">undefined</span></span><br><span class="line"><span class="number">5.</span> <span class="literal">null</span></span><br><span class="line"><span class="number">6.</span> symbol -&gt; 创建唯一值 </span><br><span class="line"><span class="keyword">let</span> val = <span class="built_in">Symbol</span>(<span class="string">&#x27;00&#x27;</span>) </span><br><span class="line"><span class="built_in">console</span>.log(val === val) <span class="literal">true</span> </span><br><span class="line"><span class="built_in">console</span>.log( <span class="built_in">Symbol</span>(<span class="string">&#x27;00&#x27;</span>) === <span class="built_in">Symbol</span>(<span class="string">&#x27;00&#x27;</span>)) <span class="literal">false</span></span><br><span class="line"><span class="number">7.</span> bigint -&gt; 在一个数值后面加n 就是bigint</span><br></pre></td></tr></table></figure>
<h3 id="引用数据类型-复杂类型"><a href="#引用数据类型-复杂类型" class="headerlink" title="引用数据类型(复杂类型)"></a>引用数据类型(复杂类型)</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> object &#123;&#125;普通对象 []数组对象 <span class="comment">// 正则对象 日期对象 等等</span></span><br><span class="line"><span class="number">2.</span> <span class="function"><span class="keyword">function</span></span></span><br></pre></td></tr></table></figure>
<h2 id="代码的运行"><a href="#代码的运行" class="headerlink" title="代码的运行"></a>代码的运行</h2><h3 id="基本数据类型"><a href="#基本数据类型" class="headerlink" title="基本数据类型"></a>基本数据类型</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 浏览器 之所以能够运行代码 是因为提供了一个供代码运行环境</span><br><span class="line"><span class="number">2.</span> 这个运行环境 -&gt; 叫 栈内存 ECStack(Execution Context Stack)</span><br><span class="line"><span class="number">3.</span> 栈内存 就是在计算机中内存中分配出来的一块内存 用来执行我们的代码 </span><br><span class="line"><span class="number">4.</span> 代码的执行 分为 全局代码 函数中代码 私有块中的代码 不同的代码执行 都有自己的上下文(环境) 这个上下文环境 叫EC(Execution Context)</span><br><span class="line"><span class="number">5.</span> 当我们的代码开始执行的时候 一开始 就会生成一个 EC(G)的全局执行上下文环境 用来执行我们的全局代码 之后 这个环境会进栈 因为代码都是在我们的栈内存中执行的</span><br><span class="line"><span class="number">6.</span> 进栈之后 我们会创建VO(G) 全局变量对象 代码在当前上下文中执行的时候 创建的变量会存储在当前上下文中指定的变量对象中 所以变量对象 就是用来存储当前上下文中创建的变量的</span><br><span class="line"><span class="number">7.</span> 以上环境都好了 开始执行代码之前 要变量提升 / 词法解析 等一些列 然后才开始执行 代码</span><br><span class="line"><span class="number">8.</span> 赋值的详细步骤 <span class="keyword">var</span> a = <span class="number">12</span> </span><br><span class="line">+ 创建一个值<span class="number">12</span> 把它存储起来(基本数据类型是存储在栈内存中)</span><br><span class="line">+ 声明一个变量 把它存储到当前上下文所属的变量对象中</span><br><span class="line">+ 最后进行等号赋值(定义) 本质上也是一个指针指向的过程</span><br></pre></td></tr></table></figure>
<p><img src="1.bmp" alt=""></p>
<h3 id="复杂数据类型"><a href="#复杂数据类型" class="headerlink" title="复杂数据类型"></a>复杂数据类型</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 基本上前面几个步骤还是一样的 创建执行环境栈(GO) 创建全局变量对象 然后代码执行</span><br><span class="line"><span class="number">2.</span> 这里只不过 我们的数据类型是引用数据类型 不会直接存储在栈内存中 会开辟一个堆内存 用来存储自己的键值对 每一个堆内存都有一个<span class="number">16</span>进制的地址</span><br><span class="line"><span class="number">3.</span> 在堆内存中分别存储键值对</span><br><span class="line"><span class="number">4.</span> 把<span class="number">16</span>进制地址放到栈中 供变量调用</span><br></pre></td></tr></table></figure>
<p><img src="2.bmp" alt=""></p>
<h3 id="小知识点"><a href="#小知识点" class="headerlink" title="小知识点"></a>小知识点</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">obj[<span class="string">&#x27;name&#x27;</span>] -&gt; 获取成员为name的属性值</span><br><span class="line">obj[name] -&gt; 把name变量存储的值 作为成员获取其属性值</span><br><span class="line">对象的属性名 可以是字符串 symbol 数字/布尔/<span class="literal">null</span>/<span class="literal">undefined</span> 等基本数据类型值</span><br><span class="line">对于普通的对象来讲 属性名不能是引用数据类型的值(比如对象)</span><br><span class="line">优先级</span><br><span class="line"><span class="keyword">var</span> a = b =<span class="number">12</span> 这个顺序是从右向左的</span><br><span class="line">a.x = a = <span class="number">12</span> <span class="comment">//这种 a.x的优先级高也就让a.x = 12 先算 在算 a = 12</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line">va obj = &#123;</span><br><span class="line">    name:<span class="string">&#x27;xxx&#x27;</span></span><br><span class="line">&#125;</span><br><span class="line"><span class="keyword">var</span> o1 = &#123;</span><br><span class="line">    age:<span class="number">12</span></span><br><span class="line">&#125;</span><br><span class="line">obj[o1] = <span class="number">100</span></span><br><span class="line"><span class="comment">// 由于o1作为属性名 给了obj对象 但O1的值 是个对象 根据我们上面写的 会转换成字符串 所以打印出来是</span></span><br><span class="line">obj&#123;</span><br><span class="line">    name:<span class="string">&#x27;xxx&#x27;</span>,</span><br><span class="line">    <span class="string">&quot;[object object]&quot;</span>:<span class="number">100</span>    </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line"><span class="keyword">var</span> a = &#123;&#125;</span><br><span class="line">b=<span class="string">&#x27;0&#x27;</span> c=<span class="number">0</span></span><br><span class="line">a[b] = <span class="string">&quot;珠峰&quot;</span> <span class="comment">//相当于 a[&#x27;0&#x27;] = 珠峰</span></span><br><span class="line">a[c] = <span class="string">&#x27;培训&#x27;</span> <span class="comment">//相当于 a[0] = 培训</span></span><br><span class="line"><span class="comment">//刚刚我们讲过对象的属性名 字符串&#x27;0&#x27;和数字0 是一个效果 也会转换成为字符串</span></span><br><span class="line"><span class="built_in">console</span>.log(a[b]) <span class="comment">//结果是 培训</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line"><span class="keyword">var</span> a=&#123;&#125;,</span><br><span class="line">    b=<span class="built_in">Symbol</span>(<span class="string">&#x27;1&#x27;</span>),</span><br><span class="line">    c=<span class="built_in">Symbol</span>(<span class="string">&#x27;1&#x27;</span>);  </span><br><span class="line"><span class="comment">//以上b和c都是 Symbol 都是唯一的 所以 b != c</span></span><br><span class="line">a[b]=<span class="string">&#x27;珠峰&#x27;</span>;</span><br><span class="line">a[c]=<span class="string">&#x27;培训&#x27;</span>;  </span><br><span class="line"><span class="built_in">console</span>.log(a[b]); <span class="comment">//打印还是 培训</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line"><span class="keyword">var</span> a=&#123;&#125;, b=&#123;<span class="attr">n</span>:<span class="string">&#x27;1&#x27;</span>&#125;, c=&#123;<span class="attr">m</span>:<span class="string">&#x27;2&#x27;</span>&#125;;  </span><br><span class="line">a[b]=<span class="string">&#x27;珠峰&#x27;</span>; b是对象 变成属性名就是 a[<span class="string">&#x27;[object object]&#x27;</span>] = 珠峰</span><br><span class="line">a[c]=<span class="string">&#x27;培训&#x27;</span>; c也是对象 变成属性名是 a[<span class="string">&#x27;[object object]&#x27;</span>] = 培训</span><br><span class="line"><span class="built_in">console</span>.log(a[b]); <span class="comment">//培训</span></span><br></pre></td></tr></table></figure>
<h2 id="全局对象"><a href="#全局对象" class="headerlink" title="全局对象"></a>全局对象</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 浏览器在最开始加载代码的时候 不仅提供了一个栈内存 供代码执行 而且还默认开辟了一个堆内存 存储一些内置的属性和方法(GO Global <span class="built_in">Object</span>)全局对象 这堆内存的地址给了<span class="built_in">window</span></span><br><span class="line"><span class="number">2.</span> 也就是说我们的全局变量对象上(VO)在刚开是的时候就有一个叫<span class="built_in">window</span>的变量 指向了我们的GO 也就是我们上面说的那个堆内存</span><br><span class="line"><span class="number">3.</span> 我们刚刚知道在占执行期上下文的时候 还产生一个全局变量对象 用来存放我们的全局代码的变量 这个 跟我们的全局对象是两个概念 全局对象指的是我们的WINDOW</span><br></pre></td></tr></table></figure>
<h3 id="声明变量都做了什么"><a href="#声明变量都做了什么" class="headerlink" title="声明变量都做了什么"></a>声明变量都做了什么</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 在全局上下文中 基于 <span class="keyword">var</span> 和 <span class="function"><span class="keyword">function</span> 声明的全局变量 也会给<span class="title">GO</span>(<span class="params"><span class="built_in">window</span></span>)中新增一个对象的私有属性(<span class="params">这里切记 基于<span class="keyword">var</span> 和 <span class="keyword">function</span>才会这样 如果是<span class="keyword">let</span> <span class="keyword">const</span> 声明的 就不会给<span class="built_in">window</span>中添加私有属性</span>)</span></span><br><span class="line"><span class="function">2. 这个<span class="title">window</span>中新增的私有属性 会和我们刚刚声明的全局变量 有 映射机制 一个变 另外一个也会变</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">var</span> a = <span class="number">10</span> </span><br><span class="line"><span class="comment">//声明了一个全局变量a  给我们的window上也增加了一个私有属性a</span></span><br><span class="line"><span class="built_in">console</span>.log(a)</span><br><span class="line"><span class="comment">// 首先看看a是否为全局变量 如果是 按照全局变量处理 如果不是全局变量 再看看 是否是window中的一个属性 如果也不是 则报错 a is not defined</span></span><br></pre></td></tr></table></figure>
<h2 id="函数的底层运行机制"><a href="#函数的底层运行机制" class="headerlink" title="函数的底层运行机制"></a>函数的底层运行机制</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">var</span> x = [<span class="number">12</span>, <span class="number">23</span>];</span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params">y</span>) </span>&#123;</span><br><span class="line">    y[<span class="number">0</span>] = <span class="number">100</span>;</span><br><span class="line">    y = [<span class="number">100</span>];</span><br><span class="line">    y[<span class="number">1</span>] = <span class="number">200</span>;</span><br><span class="line">    <span class="built_in">console</span>.log(y); <span class="comment">//输出[100,200]</span></span><br><span class="line">&#125;</span><br><span class="line">fn(x);</span><br><span class="line"><span class="built_in">console</span>.log(x); <span class="comment">//[100,23]</span></span><br></pre></td></tr></table></figure>
<h3 id="创建函数"><a href="#创建函数" class="headerlink" title="创建函数"></a>创建函数</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 这里因为函数也是引用类型的数据 所以 我们在创建函数的时候 也就是声明函数的时候 还会开辟一块 堆内存  然后把地址存放在栈内存中 </span><br><span class="line"><span class="number">2.</span> 堆内存中 存放的是函数体里面的代码 会当作字符串 这里当然也有键值对的情况 创建好了之后就等着函数被调用了</span><br><span class="line"><span class="number">3.</span> 在创建的函数的时候 我们就已经声明了函数的作用域 指就是我们函数所在的上下文 </span><br><span class="line"><span class="number">4.</span> 比如我们上面的的代码 我们的函数 所处的上下文 就是EC(G)</span><br><span class="line"><span class="number">5.</span> 函数创建了 单步执行 就是相当于存放了一大堆的字符串 一点用都没有</span><br></pre></td></tr></table></figure>
<p><img src="3.bmp" alt=""></p>
<h3 id="执行函数"><a href="#执行函数" class="headerlink" title="执行函数"></a>执行函数</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 函数执行的目的是 把之前创建的函数时候 在函数体中存储的代码字符串去执行</span><br><span class="line"><span class="number">2.</span> 首先会形成一个全新的私有的上下文 比如我们在全局代码执行的时候 会形成一个EC(G)的全局上下文 这里也是一样的</span><br><span class="line"><span class="number">3.</span> 自己私有的上下文 创建好了之后 还会生成一个自己私有的 私有变量对象控件 叫AO 这就就是存放我们的内部的私有变量 比如 形参 比如 在函数体内部 声明的变量</span><br><span class="line"><span class="number">4.</span> 然后开始进栈 准备执行 执行之前我还有好多事情去做</span><br><span class="line"><span class="number">5.</span> 初始化作用域链 作用域两是一个两端的结构 左边是当前函数执行的时候自己生成的上下文 右端是你函数创建的时候 所在的作用域  这样就可以说明 当我们查找变量的时候 先去自己的执行上下文 中去找 如果没有 就看看作用域链 去自己的作用域中去找 如果在没有 就接着向上找 </span><br><span class="line"><span class="number">6.</span> 初始化 <span class="built_in">this</span>指向 初始化 <span class="built_in">arguments</span> 形参赋值 变量提升 等</span><br><span class="line"><span class="number">7.</span> 然后执行</span><br><span class="line"><span class="number">8.</span> 执行完毕之后 为了优化栈内存 会把形成的私有上下文 出栈释放掉(GC浏览器垃圾回收机制)</span><br></pre></td></tr></table></figure>
<p><img src="2.png" alt=""></p>
<h2 id="数据类型转换规则"><a href="#数据类型转换规则" class="headerlink" title="数据类型转换规则"></a>数据类型转换规则</h2><h3 id="把其他数据类型转换为number"><a href="#把其他数据类型转换为number" class="headerlink" title="把其他数据类型转换为number"></a>把其他数据类型转换为number</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 特定需要转换为number的</span><br><span class="line"> +<span class="built_in">Number</span>([val])</span><br><span class="line"> +<span class="built_in">parseInt</span>/<span class="built_in">parseFloat</span>([val])</span><br><span class="line"><span class="number">2.</span> 隐式转换(浏览器内部默认要先转为<span class="built_in">Number</span>在进行计算)</span><br><span class="line">  +<span class="built_in">isNaN</span>([val])</span><br><span class="line">  +数学运算</span><br></pre></td></tr></table></figure>
<h3 id="把其他数据类型转换为字符串"><a href="#把其他数据类型转换为字符串" class="headerlink" title="把其他数据类型转换为字符串"></a>把其他数据类型转换为字符串</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span>能使用的方法 toString() <span class="built_in">String</span>()</span><br><span class="line"><span class="number">2.</span>隐式转换 加号运算的时候 如果某一边出现字符串 则式字符串拼接 </span><br><span class="line">把对象转换为数字 需要先toString()转换为字符串 在去转换为数字</span><br></pre></td></tr></table></figure>
<h3 id="把其他数据转换为布尔"><a href="#把其他数据转换为布尔" class="headerlink" title="把其他数据转换为布尔"></a>把其他数据转换为布尔</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 基于以下方式可以把其他数据类型转换为布尔 !转换为布尔值后取反 boolean([val])</span><br><span class="line"><span class="number">2.</span> 隐式转换 在循环或者条件判断中 条件处理的结果就式布尔类型值</span><br><span class="line"><span class="number">3.</span> 规则 只有 <span class="number">0</span> <span class="literal">NaN</span> <span class="literal">null</span> <span class="literal">undefined</span> 空字符串 五个之转换会变成布尔</span><br></pre></td></tr></table></figure>
<h3 id="在-比较过程中-数据转换的规则"><a href="#在-比较过程中-数据转换的规则" class="headerlink" title="在==比较过程中 数据转换的规则"></a>在==比较过程中 数据转换的规则</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span>类型一样的几个特点 </span><br><span class="line">&#123;&#125; == &#123;&#125; <span class="literal">false</span> 对象比较的是堆内存中的地址</span><br><span class="line">[] == [] <span class="literal">false</span></span><br><span class="line"><span class="literal">NaN</span> == <span class="literal">NaN</span> <span class="literal">false</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 类型不一样的转换规则</span><br><span class="line"><span class="literal">null</span> == <span class="literal">undefined</span> <span class="literal">true</span> 但是 <span class="literal">null</span> ==== <span class="literal">undefined</span> 结果是<span class="literal">false</span>(因为类型不一样)</span><br><span class="line">剩下的<span class="literal">null</span> / <span class="literal">undefined</span> 和其他任何数据类型值都不相等</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">3.</span>字符串 == 对象  要先把对象转换为字符串</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">4.</span> 剩下的如果 == 两边数据类型不一样 都是要转换为 数字在进行比较</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line">[] == <span class="literal">false</span> </span><br><span class="line">对象 == 布尔 两边类型不相等 都转换为数字 </span><br><span class="line">对象转换为数字 先转换为字符串(先基于valueOf获得原始值 如果没有在去toString) 在转换为数字 空数组变成字符串 为 空字符串 <span class="string">&#x27;&#x27;</span>字符串转成数字为<span class="number">0</span> <span class="literal">false</span>转换为数字为<span class="number">0</span></span><br></pre></td></tr></table></figure>
<h3 id="对象转换为字符串"><a href="#对象转换为字符串" class="headerlink" title="对象转换为字符串"></a>对象转换为字符串</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> &#123;&#125; 在转换为字符串的时候 为 <span class="string">&quot;[object object]&quot;</span> 其余的都是用双引号包裹起来</span><br><span class="line"><span class="number">2.</span> 因为对象在转为字符串的时候 调取的toString方法 是调取<span class="built_in">Object</span>.prototype.toString 而这个方法 是检测数据类型的</span><br></pre></td></tr></table></figure>
<h3 id="把其他类型转换为数字"><a href="#把其他类型转换为数字" class="headerlink" title="把其他类型转换为数字"></a>把其他类型转换为数字</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="built_in">Number</span>(<span class="string">&#x27;&#x27;</span>) <span class="number">0</span>  <span class="built_in">Number</span>(<span class="string">&#x27;10&#x27;</span>) <span class="number">10</span> <span class="built_in">Number</span>(<span class="string">&#x27;10px&#x27;</span>) <span class="literal">NaN</span> </span><br><span class="line"><span class="built_in">Number</span>(<span class="literal">true</span>) <span class="number">1</span> <span class="built_in">Number</span>(<span class="literal">false</span>) <span class="number">0</span> <span class="built_in">Number</span>(<span class="literal">null</span>) <span class="number">0</span></span><br><span class="line"><span class="built_in">Number</span>(<span class="literal">undefined</span>) <span class="literal">NaN</span> </span><br><span class="line"><span class="built_in">Number</span>(<span class="built_in">Symbol</span>(<span class="number">10</span>)) <span class="comment">//转不了symbol 报错</span></span><br><span class="line"><span class="comment">//对象变为数字 应该先valueOf获取原始值 如果没有原始值 在toString 变为字符串 最后把字符串变为数字</span></span><br></pre></td></tr></table></figure>
<h3 id="parseInt机制"><a href="#parseInt机制" class="headerlink" title="parseInt机制"></a>parseInt机制</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 把转换的值先转换为字符串 </span><br><span class="line"><span class="number">2.</span> 机制就从字符串的左侧第一个字符串开始 查找有效数字字符 遇到非有效数字 就停止不在找了 把找到的有效数字字符转换为数字 一个都没有找到 结果是<span class="literal">NaN</span></span><br><span class="line"><span class="number">3.</span> <span class="built_in">parseFloat</span> 比 <span class="built_in">parseInt</span> 多检测一个小数点</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line"><span class="built_in">parseInt</span>(<span class="string">&#x27;1.2px&#x27;</span>) <span class="comment">// 1</span></span><br><span class="line"><span class="built_in">parseInt</span>(<span class="string">&#x27;&#x27;</span>) <span class="comment">//NaN 先从字符串左侧开始找到有限数字 如果找不到 就返回NaN 所以结果是NaN</span></span><br><span class="line"><span class="built_in">Number</span>(<span class="string">&#x27;&#x27;</span>) <span class="comment">//0</span></span><br><span class="line"><span class="built_in">isNaN</span>(<span class="string">&#x27;&#x27;</span>) <span class="comment">// false这个会隐式转换为Number 是 0 0 不是NaN 所以是fanlse</span></span><br><span class="line">ParseInt(<span class="literal">null</span>)<span class="comment">// NaN 先转换为字符串为 &#x27;null&#x27;然后从左侧第一个开始查找  找不到有限数字 结果是NaN</span></span><br><span class="line"><span class="built_in">Number</span>(<span class="literal">null</span>) <span class="comment">// 0</span></span><br><span class="line"><span class="built_in">isNaN</span>(<span class="literal">null</span>) <span class="comment">//false</span></span><br><span class="line"><span class="built_in">parseInt</span>(<span class="string">&#x27;12px&#x27;</span>) <span class="comment">// 12</span></span><br><span class="line"><span class="built_in">Number</span>(<span class="string">&#x27;12px&#x27;</span>) <span class="comment">//NaN</span></span><br><span class="line"><span class="built_in">isNaN</span>(<span class="string">&#x27;12px&#x27;</span>)<span class="comment">// true</span></span><br><span class="line"><span class="built_in">isNaN</span>(<span class="built_in">Number</span>(!!<span class="built_in">Number</span>(<span class="built_in">parseInt</span>(<span class="string">&#x27;0.8&#x27;</span>)))) <span class="comment">//false</span></span><br><span class="line"><span class="comment">//parseInt(&#x27;0.8&#x27;) -&gt; 0</span></span><br><span class="line"><span class="comment">//!!Number(0) -&gt; false</span></span><br><span class="line"><span class="comment">//Number(false) -&gt; 0</span></span><br><span class="line"><span class="comment">// isNaN(0) -&gt; false </span></span><br><span class="line"><span class="keyword">typeof</span> !<span class="built_in">parseInt</span>(<span class="literal">null</span>) + !<span class="built_in">isNaN</span>(<span class="literal">null</span>)</span><br><span class="line"><span class="comment">//!parseInt(null) -&gt; !NaN -&gt; true</span></span><br><span class="line"><span class="comment">//typeof true -&gt; &#x27;boolean&#x27;</span></span><br><span class="line"><span class="comment">// !isNaN(null) -&gt;  isNaN(null) -&gt; !false -&gt; true </span></span><br><span class="line"><span class="comment">// &#x27;booleantrue&#x27;</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line"><span class="keyword">let</span> result = <span class="number">10</span> +  <span class="literal">false</span> + <span class="literal">undefined</span> + [] + <span class="string">&#x27;Tencent&#x27;</span>  + <span class="literal">true</span> + &#123;&#125;</span><br><span class="line"><span class="number">10</span> + <span class="function"><span class="params">false</span> =&gt;</span> <span class="number">10</span> + <span class="number">0</span> =&gt;<span class="number">10</span></span><br><span class="line"><span class="number">10</span> + <span class="function"><span class="params">undefined</span> =&gt;</span> <span class="number">10</span> + <span class="function"><span class="params">NaN</span> =&gt;</span> <span class="literal">NaN</span></span><br><span class="line"><span class="literal">NaN</span> + [] =&gt; <span class="literal">NaN</span> + <span class="string">&#x27;&#x27;</span> =&gt; <span class="string">&#x27;NaN&#x27;</span></span><br><span class="line"><span class="comment">//后面的 就都是字符串拼接了</span></span><br><span class="line"><span class="string">&#x27;NaNTencentTencentTencenttrue[object object]&#x27;</span></span><br></pre></td></tr></table></figure>
<h3 id="小知识"><a href="#小知识" class="headerlink" title="小知识"></a>小知识</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">+ 号 即使一边出现字符串 或者对象 也不一定是字符串拼接 ++/+ 这种情况</span><br><span class="line"><span class="built_in">console</span>.log(++<span class="string">&#x27;10&#x27;</span>) <span class="comment">//11</span></span><br><span class="line"><span class="built_in">console</span>.log(+<span class="string">&#x27;10&#x27;</span>) <span class="comment">//number 10</span></span><br><span class="line">&#123;&#125; + <span class="number">0</span> <span class="comment">//0 会把左边的&#123;&#125; 认为是一个代码块 不参与运算 只算+0</span></span><br><span class="line"><span class="number">0</span> + &#123;&#125; <span class="comment">//&quot;0 [object object]&quot;  这是数学运算</span></span><br></pre></td></tr></table></figure>
<h2 id="变量声明"><a href="#变量声明" class="headerlink" title="变量声明"></a>变量声明</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 变量声明一共有<span class="number">5</span>种方案 <span class="keyword">var</span> <span class="function"><span class="keyword">function</span> <span class="title">let</span> <span class="title">const</span> <span class="title">import</span></span></span><br><span class="line"><span class="function">2. <span class="title">let</span> 和 <span class="title">const</span> 声明的都是变量 <span class="title">const</span> 声明的变量是不允许指针重新指向的(<span class="params">但是存储的值是可以改变的 比如 存储的值是引用数据类型 可以基于地址改变堆内存种的信息</span>)</span></span><br><span class="line"><span class="function">3. 我们赋值本身 就是指针关联或者指针指向的过程</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// var  和 let 的区别</span></span><br><span class="line"> + <span class="keyword">var</span> fuction 存在变量提升 <span class="keyword">let</span> 和 <span class="keyword">const</span> 不存在</span><br><span class="line"> + 在相同的上下文种 <span class="keyword">let</span> 是不允许重复声明的 (而且检测是否重复声明 是发生在词法解析阶段) 词法解析 -&gt; 变量提升 -&gt; 代码执行</span><br><span class="line"> + 暂时性死区 (浏览器遗留的BUG) 基于<span class="keyword">typeof</span> 检测一个未被声明的变量 不会报错 结果是<span class="literal">undefined</span></span><br><span class="line"> + 除了函数或者对象的大括号之外 如果括号中 出现<span class="keyword">let</span> / <span class="keyword">const</span> / <span class="function"><span class="keyword">function</span> 则会产生块级私有上下文 当前块级上下文也只是对 <span class="title">let</span> / <span class="title">const</span> / <span class="function"><span class="keyword">function</span> 他们声明的变量有作用</span></span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//变量提升阶段</span></span><br><span class="line"><span class="built_in">console</span>.log(fn) <span class="comment">// undefined</span></span><br><span class="line"><span class="keyword">if</span>( <span class="number">1</span>== <span class="number">1</span>)&#123;</span><br><span class="line">    <span class="built_in">console</span>.log(fn) <span class="comment">//函数 私有的</span></span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>) </span>&#123; <span class="built_in">console</span>.log(<span class="string">&#x27;ok&#x27;</span>)&#125;</span><br><span class="line">    fn = <span class="number">12</span></span><br><span class="line">    <span class="built_in">console</span>.log(fn) <span class="comment">//12</span></span><br><span class="line">&#125;</span><br><span class="line"><span class="built_in">console</span>.log(fn) <span class="comment">//函数</span></span><br><span class="line">老版本浏览器 不管条件是否成立 变量 和 函数都会提升 函数也会定义</span><br><span class="line">新版本 不管条件是否成立 函数都会提升 但不会赋值(比如在判断体 循环体 代码块 ) 他只会进行声明 不会赋值和定义</span><br><span class="line">如果以上的大括号种出现了<span class="function"><span class="keyword">function</span> <span class="title">xxx</span>(<span class="params"></span>)</span>&#123;&#125; 此时当前大括号会形成一个私有的上下文 第一件事情 就是变量提升 他会把函数声明 加定义</span><br></pre></td></tr></table></figure>
<p><img src="函数的超级变态机制.png" alt=""></p>
<h2 id="变量提升机制"><a href="#变量提升机制" class="headerlink" title="变量提升机制"></a>变量提升机制</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 变量提升发生在 当前上下文中 (全局/私有/块级) js代码自上而下执行之前浏览器会提前处理一些事情</span><br><span class="line"><span class="number">2.</span> 带<span class="keyword">var</span>的 只会提前声明  带<span class="function"><span class="keyword">function</span>的会 提前声明加定义 就是函数整体提升</span></span><br><span class="line"><span class="function">3. 函数表达式的方式 <span class="title">var</span> <span class="title">fn</span> = <span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;&#125; 只是会吧<span class="title">fn</span>的变量 提升</span></span><br><span class="line"><span class="function">4. <span class="title">let</span> 和 <span class="title">const</span>  是不进行变量提升的 只有带<span class="title">var</span> 和<span class="title">functiond</span>的才会</span></span><br><span class="line"><span class="function">5. 基于全局上下文中声明的变量 和函数 会映射到全局变量 <span class="title">window</span>上一份 作为它的属性 一个修改 另外一个也修改</span></span><br><span class="line"><span class="function">6. 不论条件是否成立 都要进行变量提升</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//具名话 针对于函数表达式 </span></span><br><span class="line"><span class="number">1.</span> 我们原本 函数表达式 后面会写一个 匿名函数 但是现在 我们写了一个AAA的名字</span><br><span class="line"><span class="keyword">var</span> func = <span class="function"><span class="keyword">function</span> <span class="title">AAA</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="comment">//但是这个具名的话的函数名字 可以在自己的当前上下文执行</span></span><br><span class="line">    <span class="comment">//可以递归使用</span></span><br><span class="line">    AAA()</span><br><span class="line">&#125;	</span><br><span class="line"><span class="number">2.</span> 但是这个名字 在全局 是没有作用的</span><br><span class="line">AAA() <span class="comment">//AAA调用 会报错</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// let  和 const 没有 变量提升 所以 报错也不一样</span></span><br><span class="line"><span class="built_in">console</span>.log(a) <span class="comment">// Cannot access &#x27;a&#x27; before initialization</span></span><br><span class="line"><span class="keyword">let</span> a = <span class="number">12</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 不论条件是否成立 都要进行变量提升(细节点:条件中带function的在新版本浏览器中只会提前声明 不会在提前赋值了)</span></span><br><span class="line"><span class="number">1.</span> 这里 就是 你下面不管条件是否成立不成立 都要提升一个a变量</span><br><span class="line"><span class="keyword">if</span>(!(<span class="string">&#x27;a&#x27;</span> <span class="keyword">in</span> <span class="built_in">window</span>))&#123;</span><br><span class="line">    <span class="keyword">var</span> a = <span class="number">1</span></span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;&#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="built_in">console</span>.log(a)</span><br><span class="line">[老版本 浏览器]</span><br><span class="line"><span class="keyword">var</span> a fn = 函数</span><br><span class="line">[新版本 浏览器(IE10以上)]</span><br><span class="line"><span class="keyword">var</span> a fn</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line">fn()</span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;<span class="built_in">console</span>.log(<span class="number">1</span>)&#125;</span><br><span class="line">fn()</span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;<span class="built_in">console</span>.log(<span class="number">2</span>)&#125;</span><br><span class="line">fn()</span><br><span class="line"><span class="keyword">var</span> fn = <span class="function"><span class="keyword">function</span> (<span class="params"></span>)</span>&#123;<span class="built_in">console</span>.log(<span class="number">3</span>)&#125;</span><br><span class="line">fn()</span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;<span class="built_in">console</span>.log(<span class="number">4</span>)&#125;</span><br><span class="line">fn()</span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;<span class="built_in">console</span>.log(<span class="number">5</span>)&#125;</span><br><span class="line">fn()</span><br><span class="line"><span class="comment">/* EC(G)</span></span><br><span class="line"><span class="comment">* 1. 首先函数整体提升 fn()都上去了</span></span><br><span class="line"><span class="comment">* 2. 当走到 var fn = function ()&#123;console.log(3)&#125; 发现已经有fn的函数了  就先不处理</span></span><br><span class="line"><span class="comment">* 3. 然后代码开始执行 前三个fn调用输出 都是5 </span></span><br><span class="line"><span class="comment">* 4. 当走到 fn = function ()&#123;console.log(3)&#125; 开始给fn函数重新赋值了 所以后三个输出都是3</span></span><br><span class="line"><span class="comment">*/</span></span><br></pre></td></tr></table></figure>
<h3 id="块级作用域的变量提升机制"><a href="#块级作用域的变量提升机制" class="headerlink" title="块级作用域的变量提升机制"></a>块级作用域的变量提升机制</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 如果我们的代码 出现在了除函数 和 对象意外的花括号里面 那么就会产生一个块级上下文</span><br><span class="line"><span class="number">2.</span> 新版本浏览器中 如果出现在块级作用域里面的代码 那么变量只声明不复制</span><br><span class="line"><span class="number">3.</span> 当我们执行代码的时候 会产生映射机制 也就是出现在块级作用域里的变量声明 或者函数执行的 之前的代码 都会映射到全局 而之后的代码 都会是私有的</span><br></pre></td></tr></table></figure>
<p><img src="1-2.bmp" alt=""></p>
<h3 id="形参默认值"><a href="#形参默认值" class="headerlink" title="形参默认值"></a>形参默认值</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 如果我们的函数形参有默认值了 而且 我们函数里有<span class="keyword">var</span>声明的了变量 那么这个声明的变量将会形成一个块级作用域</span><br><span class="line"><span class="number">2.</span> 如果是<span class="keyword">let</span> 声明的变量 那么就会报错</span><br><span class="line"><span class="number">3.</span> 并且块级私有上下文的上级上下文 就是函数的私有上下文</span><br></pre></td></tr></table></figure>
<p><img src="1-4.png" alt=""></p>
<h2 id="闭包作用域和高级编程技巧"><a href="#闭包作用域和高级编程技巧" class="headerlink" title="闭包作用域和高级编程技巧"></a>闭包作用域和高级编程技巧</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 一般情况下 函数执行完成之后 所有形成的私有上下文 都会出栈释放 私有上下文中的一切内容都会被销毁 主要是为了优化栈内存控件</span><br><span class="line"><span class="number">2.</span> 特殊情况 如果函数执行所形成上下文中 有一个东西(引用类型的空间地址) 被当前上下文 以外的事物所占用 那么当前上下文 是不能被释放的 上下文中的信息保留下来了(包含私有变量) 导致栈内存空间变大 如果返回的地址还会被执行一次 所以也临时不会释放 当 外部用完 就会释放</span><br><span class="line"><span class="number">3.</span> 函数每次执行 都会形成一个全新的私有上下文</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">let</span> x = <span class="number">5</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span> (<span class="params">x</span>)</span>&#123;</span><br><span class="line">    <span class="comment">//这里的return 就当是在堆内存中又开辟了一个空间 把函数的地址返回了</span></span><br><span class="line">    <span class="keyword">return</span> <span class="function"><span class="keyword">function</span>(<span class="params">y</span>)</span>&#123;</span><br><span class="line">        <span class="built_in">console</span>.log(y + (++x))</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="keyword">let</span> f = fn(<span class="number">6</span>) <span class="comment">//这里其实就是返回了一个地址 而这种就是我们上面所说的 特殊情况</span></span><br><span class="line">f(<span class="number">7</span>)</span><br><span class="line">fn(<span class="number">8</span>)(<span class="number">9</span>)</span><br><span class="line">f(<span class="number">10</span>)</span><br><span class="line"><span class="built_in">console</span>.log(x)</span><br></pre></td></tr></table></figure>
<p><img src="闭包.png" alt=""></p>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">let</span> a = <span class="number">0</span> b =<span class="number">0</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">A</span> (<span class="params">a</span>) </span>&#123;</span><br><span class="line">    <span class="comment">//这种地址也会被引用 因为在大A是全局的变量 执行到这里的时候 我们相当于把A的地址又重新赋值了</span></span><br><span class="line">    A = <span class="function"><span class="keyword">function</span>(<span class="params">b</span>)</span>&#123;</span><br><span class="line">        alert(a + b ++)</span><br><span class="line">    &#125;</span><br><span class="line">    alert(a++)</span><br><span class="line">&#125;</span><br><span class="line"> A(<span class="number">1</span>) <span class="comment">// 弹框1</span></span><br><span class="line"> A(<span class="number">2</span>) <span class="comment">// 弹框4</span></span><br></pre></td></tr></table></figure>
<p><img src="闭包2.png" alt=""></p>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//示例</span></span><br><span class="line"><span class="keyword">var</span> buttonList = <span class="built_in">document</span>.querySelectorAll(<span class="string">&#x27;button&#x27;</span>);</span><br><span class="line"><span class="comment">/* </span></span><br><span class="line"><span class="comment">// 实现不了的，为啥？</span></span><br><span class="line"><span class="comment">//  + 循环中的i是全局的，每一轮循环给对应元素的click绑定方法（创建函数 [存储代码字符串]，此时函数没有执行）</span></span><br><span class="line"><span class="comment">//  + 循环结束的时候，全局的i=5</span></span><br><span class="line"><span class="comment">//  + 点击某个按钮，执行之前绑定的函数：此时形成一个全新的私有上下文，它的上级上下文是全局上下文，函数代码执行的过程中，遇到变量i，但是i不是自己的私有变量，找到的是全局的i，全局的i是5</span></span><br><span class="line"><span class="comment">*/</span></span><br><span class="line"><span class="keyword">for</span> (<span class="keyword">var</span> i = <span class="number">0</span>; i &lt; buttonList.length; i++) &#123;</span><br><span class="line">    buttonList[i].onclick = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">        <span class="built_in">console</span>.log(i, <span class="string">`我是第<span class="subst">$&#123;i+<span class="number">1</span>&#125;</span>个按钮~`</span>);</span><br><span class="line">    &#125;;</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">//最后每次点击按钮之后 打印出来的都是5</span></span><br></pre></td></tr></table></figure>
<p><img src="8.bmp" alt=""></p>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//解决</span></span><br><span class="line"><span class="comment">// 解决问题的思路：当点击事件触发，执行对应的函数，用到的i不要再向全局查找了；相当于自己形成一个上下文，而自己的上下文中，存储了你需要的i，存储的值是指定的索引即可  =&gt;闭包的保存机制</span></span><br><span class="line"><span class="comment">// 弊端：循环多少次，就产生多少个闭包，非常消耗内存</span></span><br><span class="line"> <span class="keyword">for</span> (<span class="keyword">var</span> i = <span class="number">0</span>; i &lt; buttonList.length; i++) &#123;</span><br><span class="line">    <span class="comment">// 每一轮循环都会把自执行函数执行，形成一个全新的私有上下文（一共形成了5个）</span></span><br><span class="line">    <span class="comment">//   + 把当前这一轮全局i的值作为实参，传递给当前形成的私有上下文中的形参n[私有变量]</span></span><br><span class="line">    <span class="comment">//   + 第一个私有上下文中的n=0，第二个私有上下文中的n=1 ....</span></span><br><span class="line">    <span class="comment">// 每一个形成的上下文中，创建的函数都被外部的元素对象的onclick占用了，所以形成了5个闭包</span></span><br><span class="line">    <span class="comment">// 当点击按钮执行函数的时候，遇到一个变量n，不是自己私有的，则找上级上下文（闭包）中的n，而n存储的值就是它的索引</span></span><br><span class="line">    (<span class="function"><span class="keyword">function</span> (<span class="params">n</span>) </span>&#123;</span><br><span class="line">        buttonList[n].onclick = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">            <span class="built_in">console</span>.log(<span class="string">`我是第<span class="subst">$&#123;n+<span class="number">1</span>&#125;</span>个按钮~`</span>);</span><br><span class="line">        &#125;;</span><br><span class="line">    &#125;)(i);</span><br><span class="line">&#125; </span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">for</span> (<span class="keyword">var</span> i = <span class="number">0</span>; i &lt; buttonList.length; i++) &#123;</span><br><span class="line">    buttonList[i].onclick = (<span class="function"><span class="keyword">function</span> (<span class="params">i</span>) </span>&#123;</span><br><span class="line">        <span class="comment">// i是每一轮形成的闭包中的私有变量，五个闭包中存储的值分别是0~4[索引]</span></span><br><span class="line">        <span class="comment">// 每一次都是把小函数返回，赋值给元素的点击事件，当点击元素的时候，执行返回的小函数</span></span><br><span class="line">        <span class="keyword">return</span> <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">            <span class="built_in">console</span>.log(<span class="string">`我是第<span class="subst">$&#123;i+<span class="number">1</span>&#125;</span>个按钮~`</span>);</span><br><span class="line">        &#125;;</span><br><span class="line">    &#125;)(i);</span><br><span class="line">&#125; </span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 还是基于“闭包的机制”，但是不是自己去执行函数构建，而是利用ES6中let产生的私有上下文实现</span></span><br><span class="line"><span class="keyword">for</span> (<span class="keyword">let</span> i = <span class="number">0</span>; i &lt; buttonList.length; i++) &#123;</span><br><span class="line">    <span class="comment">// 第一轮循环 私有块1</span></span><br><span class="line">    <span class="comment">//   + 私有变量 i = 0</span></span><br><span class="line">    <span class="comment">//   + 当前私有上下文中的创建的一个函数被全局的元素对象的onclick占用了(闭包)</span></span><br><span class="line">    <span class="comment">// ....</span></span><br><span class="line">    buttonList[i].onclick = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">        <span class="built_in">console</span>.log(<span class="string">`我是第<span class="subst">$&#123;i+<span class="number">1</span>&#125;</span>个按钮~`</span>);</span><br><span class="line">    &#125;;</span><br><span class="line">&#125; </span><br></pre></td></tr></table></figure>
<h3 id="let-的-for-循环机制"><a href="#let-的-for-循环机制" class="headerlink" title="let 的 for 循环机制"></a>let 的 for 循环机制</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 循环第一轮 会形成一个父级的私有块上下文 循环结束后就会销毁</span><br><span class="line"><span class="number">2.</span> 父级块上下文 都会把变量 传送给下面的子集上下文</span><br><span class="line"><span class="number">3.</span> 然后开始循环 每一轮都会形成一个私有块上下文 由于被我们的click 占用 所以不会销毁</span><br></pre></td></tr></table></figure>
<h3 id="事件绑定解决方案"><a href="#事件绑定解决方案" class="headerlink" title="事件绑定解决方案"></a>事件绑定解决方案</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 无论闭包还是<span class="keyword">let</span> 我们都是用闭包解决的</span><br><span class="line"><span class="number">2.</span> 还有第二种解决方案 给每个DOM对象加个自定义属性</span><br><span class="line"><span class="number">3.</span> 利用事件代理的机制（性能提高&gt;=<span class="number">40</span>%）</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"> <span class="comment">// 方案二：自定义属性（事先把一些信息存储到元素的身上，后期在一些其他的操作中，想要获取这些信息，直接基于元素的属性访问就可以拿到这些值） =&gt;操作DOM的时代下，这种方案非常常用</span></span><br><span class="line"><span class="keyword">for</span> (<span class="keyword">var</span> i = <span class="number">0</span>; i &lt; buttonList.length; i++) &#123;</span><br><span class="line">    <span class="comment">// 把当前按钮的索引存储在它的自定义属性上（每个按钮都是一个元素对象）</span></span><br><span class="line">    buttonList[i].myIndex = i;</span><br><span class="line">    buttonList[i].onclick = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">        <span class="comment">// 给当前元素的某个事件绑定方法，当事件触发，方法执行的时候，方法中的this是当前点击的按钮</span></span><br><span class="line">        <span class="built_in">console</span>.log(<span class="string">`我是第<span class="subst">$&#123;<span class="built_in">this</span>.myIndex+<span class="number">1</span>&#125;</span>个按钮~`</span>);</span><br><span class="line">    &#125;;</span><br><span class="line">&#125; </span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 方案三：利用事件代理的机制（性能提高&gt;=40%）</span></span><br><span class="line">&lt;button index=<span class="string">&quot;1&quot;</span>&gt;按钮<span class="number">1</span>&lt;/button&gt;</span><br><span class="line">&lt;button index=<span class="string">&quot;2&quot;</span>&gt;按钮<span class="number">2</span>&lt;/button&gt;</span><br><span class="line">&lt;button index=<span class="string">&quot;3&quot;</span>&gt;按钮<span class="number">3</span>&lt;/button&gt;</span><br><span class="line">&lt;button index=<span class="string">&quot;4&quot;</span>&gt;按钮<span class="number">4</span>&lt;/button&gt;</span><br><span class="line"><span class="built_in">document</span>.body.onclick = <span class="function"><span class="keyword">function</span> (<span class="params">ev</span>) </span>&#123;</span><br><span class="line">    <span class="keyword">let</span> target = ev.target;</span><br><span class="line">    <span class="comment">// 点击的是按钮</span></span><br><span class="line">    <span class="keyword">if</span> (target.tagName === <span class="string">&quot;BUTTON&quot;</span>) &#123;</span><br><span class="line">        <span class="keyword">let</span> index = target.getAttribute(<span class="string">&#x27;index&#x27;</span>);</span><br><span class="line">        <span class="built_in">console</span>.log(<span class="string">`我是第<span class="subst">$&#123;+index+<span class="number">1</span>&#125;</span>个按钮~`</span>);</span><br><span class="line">    &#125;</span><br><span class="line">&#125;; </span><br></pre></td></tr></table></figure>
<h2 id="短路语句"><a href="#短路语句" class="headerlink" title="短路语句"></a>短路语句</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">A || B  A的值是真 返回A的值 否则返回B的值</span><br><span class="line">A &amp;&amp; B  A的值是真 返回B的值 否则返回A的值</span><br><span class="line">如果同时存在  &amp;&amp;高于||</span><br></pre></td></tr></table></figure>
<h2 id="This"><a href="#This" class="headerlink" title="This"></a>This</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> <span class="built_in">this</span> 函数的执行主体 和执行上下文不是一个概念</span><br><span class="line"><span class="number">2.</span> 全局的<span class="built_in">this</span> 是 <span class="built_in">window</span> 我们研究中的都是函数中的<span class="built_in">this</span></span><br></pre></td></tr></table></figure>
<h3 id="this-的执行规律"><a href="#this-的执行规律" class="headerlink" title="this 的执行规律"></a>this 的执行规律</h3><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 给当前元素的某个事件行为绑定方法 事件触发 执行对应的方法 方法中的<span class="built_in">this</span> 是当前事件本身</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="built_in">document</span>.body.click = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123; <span class="comment">// this-&gt; body &#125;</span></span><br><span class="line"><span class="comment">// IE 6/7/8 基于 attachEvent 绑定的不是this 是 window</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 函数执行 首先看函数名称之前 是否有 点 有点 点前面是谁 <span class="built_in">this</span> 就是谁 如果没有 点  <span class="built_in">this</span> 就是<span class="built_in">window</span>(严格模式下 没有 点 <span class="built_in">this</span> 是 <span class="literal">undefined</span>)</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">3.</span> 自调用函数/回调函数 中的<span class="built_in">this</span> 一般都是<span class="built_in">window</span> 或者 <span class="literal">undefined</span> h</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">4.</span> 构造函数中的<span class="built_in">this</span> 是当前类的实例</span><br><span class="line"><span class="number">5.</span> 箭头函数中没有自己的<span class="built_in">this</span> 用到的<span class="built_in">this</span> 都是上下文中的<span class="built_in">this</span></span><br><span class="line"><span class="number">6.</span> 基于call / apply / bind 可以强制改变<span class="built_in">this</span>指向</span><br></pre></td></tr></table></figure>
<h2 id="arguments-形参映射机制"><a href="#arguments-形参映射机制" class="headerlink" title="arguments 形参映射机制"></a>arguments 形参映射机制</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// EC(G)</span></span><br><span class="line"><span class="keyword">var</span> = <span class="number">4</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">b</span> (<span class="params">x,y,a</span>) </span>&#123;</span><br><span class="line">    <span class="comment">// 形成自己的私有执行上下文 EC(b)</span></span><br><span class="line">    <span class="comment">// 初始化作用域链 &lt;EC(b),EC(G)&gt;</span></span><br><span class="line">    <span class="comment">//初始化this:window</span></span><br><span class="line">    <span class="comment">//初始化 arguments:&#123;0:1,1:2,2:3,length:3&#125;  左侧是真实结构 为了方便看我们携程数组[1,2,3] 这里还会和我们的形参形成映射机制</span></span><br><span class="line">    <span class="comment">// 形参赋值 x =1 y =2 a =3</span></span><br><span class="line">    <span class="comment">//变量提升</span></span><br><span class="line">    <span class="built_in">console</span>.log(a) <span class="comment">// 3</span></span><br><span class="line">    <span class="built_in">arguments</span>[<span class="number">2</span>] = <span class="number">10</span></span><br><span class="line">    <span class="built_in">console</span>.log(a) <span class="comment">//10</span></span><br><span class="line">&#125;</span><br><span class="line">a = b(<span class="number">1</span>,<span class="number">2</span>,<span class="number">3</span>)</span><br><span class="line"><span class="built_in">console</span>.log(a)</span><br></pre></td></tr></table></figure>
<h2 id="模块化-单列模式设计模式"><a href="#模块化-单列模式设计模式" class="headerlink" title="模块化 / 单列模式设计模式"></a>模块化 / 单列模式设计模式</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 在很早以前没有引用类型 比如对象 和 函数的时候 想描述个人信息的时候 就需要一个变量一个变量的去定义 这个时候 就会造成全局变量的冲突</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//比如 我们描述 欧阳花的个人信息</span></span><br><span class="line"><span class="keyword">let</span> name = <span class="string">&quot;欧阳花&quot;</span> <span class="keyword">let</span> age = <span class="number">21</span> <span class="keyword">let</span> sex = <span class="string">&#x27;男&#x27;</span></span><br><span class="line"><span class="comment">//还想描述 吴家乐的个人信息</span></span><br><span class="line"><span class="keyword">let</span> name = <span class="string">&#x27;吴家乐&#x27;</span> <span class="keyword">let</span> age = <span class="number">25</span> <span class="keyword">let</span> sex = <span class="string">&#x27;女&#x27;</span></span><br><span class="line"><span class="comment">//以上我们看到 变量就冲突了</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 所以我们开始用闭包的方式 去描述 因为 闭包里面的变量都是私有变量 不会跟外部产生冲突</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//闭包的方式去描述</span></span><br><span class="line">(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> name = <span class="string">&quot;欧阳花&quot;</span> </span><br><span class="line">    <span class="keyword">let</span> age = <span class="number">21</span> </span><br><span class="line">    <span class="keyword">let</span> sex = <span class="string">&#x27;男&#x27;</span></span><br><span class="line">&#125;)()</span><br><span class="line"></span><br><span class="line">(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> name = <span class="string">&#x27;吴家乐&#x27;</span> </span><br><span class="line">    <span class="keyword">let</span> age = <span class="number">25</span> </span><br><span class="line">    <span class="keyword">let</span> sex = <span class="string">&#x27;女&#x27;</span></span><br><span class="line">&#125;)()</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">3.</span> 但是以上 我们如果要在吴家乐那的作用域下 用到 欧阳花里面的变量  只能添加到<span class="built_in">window</span>上  这种方式 如果变量不是很多还好 </span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 真实业务开发 B 里面可能要用到 A 的方法 就需要把A的方法暴漏到windows上去</span></span><br><span class="line">A</span><br><span class="line">(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> set = <span class="number">0</span></span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;&#125;</span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">query</span> (<span class="params"></span>) </span>&#123;&#125;</span><br><span class="line">    <span class="built_in">window</span>.query = query</span><br><span class="line">&#125;)()</span><br><span class="line"></span><br><span class="line">B   里面要用到A 里面的query方法</span><br><span class="line">(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> set = <span class="number">0</span></span><br><span class="line">    <span class="built_in">window</span>.query()</span><br><span class="line">&#125;)()</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">//所以这里 我们就用暴漏对象的方法 把要使用的方法 return 出去 这种方式就叫单例模式</span></span><br><span class="line"><span class="keyword">let</span> AModule = (<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> set = <span class="number">0</span></span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">fn</span>(<span class="params"></span>)</span>&#123;&#125;</span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">query</span> (<span class="params"></span>) </span>&#123;&#125;</span><br><span class="line">   	<span class="keyword">return</span> &#123;</span><br><span class="line">        query,</span><br><span class="line">        set</span><br><span class="line">    &#125;</span><br><span class="line">&#125;)()</span><br><span class="line"><span class="comment">// B 模块</span></span><br><span class="line">(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> set = <span class="number">0</span></span><br><span class="line">    AModule.query()</span><br><span class="line">&#125;)()</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">4.</span> 在我们自己编写类库/插件/UI组件/框架的时候 为了防止全局变量污染 我们需要基于闭包的机制进行 <span class="string">&quot;私有化&quot;</span> 处理</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line">(<span class="function"><span class="keyword">function</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">function</span> <span class="title">Banner</span>(<span class="params"></span>)</span>&#123;&#125;</span><br><span class="line">    <span class="comment">//利用暂时性死区 如果一个变量没有声明 用typeof检测 是undefined(浏览器可以typeof 可以检测到window 是 &#x27;object&#x27;) 我们利用这个特点可以区分 是浏览器执行js 还是node执行js</span></span><br><span class="line">    <span class="keyword">if</span>(<span class="keyword">typeof</span> <span class="built_in">window</span> !==<span class="string">&#x27;undefined&#x27;</span>)&#123;</span><br><span class="line">         <span class="built_in">window</span>.Banner = Banner</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="comment">//如果是CommonJS / ES6Module 就会检测到下面两个东西</span></span><br><span class="line">   	<span class="keyword">if</span>(<span class="keyword">typeof</span> <span class="built_in">module</span> !== <span class="string">&#x27;undefined&#x27;</span> &amp;&amp; <span class="keyword">typeof</span> <span class="built_in">module</span>.exports !== <span class="string">&#x27;undefined&#x27;</span>)&#123;</span><br><span class="line">	<span class="built_in">module</span>.exports = Banner</span><br><span class="line">    &#125;</span><br><span class="line">&#125;)()</span><br></pre></td></tr></table></figure>
<h2 id="惰性函数"><a href="#惰性函数" class="headerlink" title="惰性函数"></a>惰性函数</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 能执行一次 绝对不会执行第二次 </span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 我们在获取元素样式的时候 用到的API 有 getComputedStyle 和 currentStyle(这个方法在IE6-8)</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">getCss</span>(<span class="params">elemnt,attr</span>)</span>&#123;</span><br><span class="line">    <span class="keyword">if</span>(<span class="built_in">window</span>.getComputedStyle)&#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="built_in">window</span>.getComputedStyle(elemnt)[attr]</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="keyword">return</span> elemnt.currentStyle[attr]</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">//然后我们开始获取元素的样式</span></span><br><span class="line"><span class="built_in">console</span>.log(getCss(<span class="built_in">document</span>.body,<span class="string">&#x27;width&#x27;</span>))</span><br><span class="line"><span class="built_in">console</span>.log(getCss(<span class="built_in">document</span>.body,<span class="string">&#x27;padding&#x27;</span>))</span><br><span class="line"><span class="built_in">console</span>.log(getCss(<span class="built_in">document</span>.body,<span class="string">&#x27;margin&#x27;</span>))</span><br><span class="line"><span class="comment">//总结 这样好么 因为我们每执行一次函数 都需要处理兼容性问题 其实没必要 因为在第一检测时候就已经知道兼容情况了 </span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">getCss</span>(<span class="params">elemnt,attr</span>)</span>&#123;</span><br><span class="line">    <span class="keyword">if</span>(<span class="built_in">window</span>.getComputedStyle)&#123;</span><br><span class="line">        <span class="comment">//走到判断 就可以判断我们是哪个浏览器的兼容了 然后改变getCss的指针</span></span><br><span class="line">        getCss = <span class="function"><span class="keyword">function</span> (<span class="params">elemnt,attr</span>) </span>&#123;</span><br><span class="line">            <span class="keyword">return</span> <span class="built_in">window</span>.getComputedStyle(elemnt)[attr]</span><br><span class="line">        &#125;</span><br><span class="line">    &#125;<span class="keyword">else</span>&#123;</span><br><span class="line">        getCss = <span class="function"><span class="keyword">function</span>(<span class="params">elemnt,attr</span>)</span>&#123;</span><br><span class="line">            <span class="keyword">return</span> elemnt.currentStyle[attr]</span><br><span class="line">        &#125;</span><br><span class="line">    &#125;</span><br><span class="line">   <span class="comment">// 改变之后 要保证我们的第一个函数要执行一次 拿到结果 </span></span><br><span class="line">   <span class="keyword">return</span> getCss(element,attr) </span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">//第一次执行函数</span></span><br><span class="line"><span class="built_in">console</span>.log(getCss(<span class="built_in">document</span>.body,<span class="string">&#x27;width&#x27;</span>))、</span><br><span class="line"><span class="comment">// 第二次走的时候 就直接走到 我们改变指针的那个函数了 </span></span><br><span class="line"><span class="built_in">console</span>.log(getCss(<span class="built_in">document</span>.body,<span class="string">&#x27;padding&#x27;</span>))</span><br><span class="line"><span class="built_in">console</span>.log(getCss(<span class="built_in">document</span>.body,<span class="string">&#x27;margin&#x27;</span>))</span><br><span class="line"><span class="comment">//以上我们 再次执行的是时候 是重构后的小函数 告别了 兼容校验的操作   只执行一次</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 惰性函数 就是函数重构的问题 第一次执行 会产生闭包 </span><br></pre></td></tr></table></figure>
<h2 id="柯里化函数"><a href="#柯里化函数" class="headerlink" title="柯里化函数"></a>柯里化函数</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 区别于惰性函数  是一个预处理的思想 应用的也是闭包的机制</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">let</span> res = fun(<span class="number">1</span>,<span class="number">2</span>)(<span class="number">3</span>)</span><br><span class="line"><span class="built_in">console</span>.log(res) <span class="comment">//求和结果 为6</span></span><br><span class="line"><span class="comment">//实现以上函数 首先第一函数执行的时候 我们不知道传进来几个参数 第二次也不知道 所以我们用剩余形参去接收</span></span><br><span class="line"><span class="comment">//然后把两个函数的参数 连接在一起 在最总进行求和</span></span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">fn</span> (<span class="params">...outerArgs</span>)</span>&#123;</span><br><span class="line">    <span class="comment">//剩余参数 会把你的实参放在一个数组中 而arguments是一个伪数组</span></span><br><span class="line">    <span class="keyword">return</span> <span class="function"><span class="keyword">function</span> <span class="title">anonymous</span>(<span class="params">...innerArgs</span>)</span>&#123;</span><br><span class="line">        <span class="keyword">let</span> arr = outerArgs.concat(innerArgs)</span><br><span class="line">        <span class="comment">// 如果reduce里面 没有传第二个形参 那么total 就是数组中的第一项 item是第二项  然后相加就变成3 然后把3作为total 在和 后面的一项相加</span></span><br><span class="line">        <span class="keyword">return</span> arr.reduce(<span class="function">(<span class="params">total,item</span>) =&gt;</span> &#123;</span><br><span class="line">            <span class="keyword">return</span> total + item</span><br><span class="line">        &#125;,这里还可以传第二个形参)</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 第一次执行大函数 形成一个闭包(原因:返回了一个小函数) 把一些信息存储到了闭包中(传递的实参信息或者当前闭包中声明的一些私有变量等信息) 等到后面需要把返回的小函数anonymous执行 遇到一些非自己私有变量 则向其上级上下文中查找</span><br></pre></td></tr></table></figure>
<h2 id="组合函数"><a href="#组合函数" class="headerlink" title="组合函数"></a>组合函数</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 把处理数据的函数像管道一样连接起来 然后让数据传过管道得到 最终的结果</span><br><span class="line"><span class="number">2.</span> 以下 就是我们把每个函数的运行结果 当作形参 传递给了下一个函数 参与了运算</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">const</span> add1 = <span class="function">(<span class="params">x</span>) =&gt;</span> x + <span class="number">1</span></span><br><span class="line"><span class="keyword">const</span> mul3 = <span class="function">(<span class="params">x</span>) =&gt;</span> x * <span class="number">3</span></span><br><span class="line"><span class="keyword">const</span> div2 = <span class="function">(<span class="params">x</span>) =&gt;</span> x / <span class="number">2</span></span><br><span class="line">div2(mul3(add1(add1(<span class="number">0</span>)))) <span class="comment">// =&gt; 3</span></span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 上面的写法可读性明显很差 我们可以构建一个compose函数 它接收任意多个函数(而这些函数都只能接收一个参数) 然后compose 返回也是一个函数 </span><br><span class="line"></span><br><span class="line"><span class="keyword">const</span> operate = compose(div2,mul3,add1,add1)</span><br><span class="line">operate(<span class="number">0</span>)   相当于 div2(mul3(add1(add1(<span class="number">0</span>))))</span><br><span class="line">operate(<span class="number">2</span>)   相当于 div2(mul3(add1(add1(<span class="number">2</span>))))</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">compose</span>(<span class="params">...func</span>)</span>&#123;</span><br><span class="line">    <span class="keyword">return</span> <span class="function"><span class="keyword">function</span> <span class="title">operate</span>(<span class="params">x</span>)</span>&#123;</span><br><span class="line">        <span class="comment">//如果你一个数据处理函数也没有传进来  那么 就直接返回你的参数</span></span><br><span class="line">        <span class="keyword">if</span>(func.length === <span class="number">0</span>) <span class="keyword">return</span> x</span><br><span class="line">        <span class="comment">//如果你只传进来一个事件处理函数 那么 我们就执行</span></span><br><span class="line">        <span class="keyword">if</span>(func.length === <span class="number">1</span>) <span class="keyword">return</span> func[<span class="number">0</span>](x)</span><br><span class="line">        <span class="comment">//这里我们要知道 我需要最先执行 func数组里的最后面的函数 然后结果当作参数传给倒数第二个函数里 一次类推 所以这里我们会用到reduce 所以先要把数组反转以下</span></span><br><span class="line">        <span class="keyword">let</span> n = <span class="number">0</span></span><br><span class="line">        func.reverse()</span><br><span class="line">        <span class="keyword">return</span> func.reduce(<span class="function">(<span class="params">result,item</span>) =&gt;</span> &#123;</span><br><span class="line">            n++</span><br><span class="line">            <span class="comment">//说明这是第一次 result是add1函数 item是你传进来的第二次个add1函数</span></span><br><span class="line">            <span class="keyword">if</span>( n === <span class="number">1</span>)&#123;</span><br><span class="line">            	<span class="keyword">return</span> item(result(x))</span><br><span class="line">            &#125;</span><br><span class="line">            <span class="keyword">return</span> item(result)</span><br><span class="line">        &#125;)</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="comment">//下面是几种情况</span></span><br><span class="line"><span class="keyword">let</span> operate = compose(div2,mul3,add1,add1)</span><br><span class="line"><span class="built_in">console</span>.log(operate(<span class="number">0</span>))  =&gt; <span class="number">3</span></span><br><span class="line"></span><br><span class="line"><span class="comment">//一个数据函数都没有传 就直接返回你的形参</span></span><br><span class="line"><span class="keyword">let</span> operate = compose(div2,mul3,add1,add1)</span><br><span class="line">operate(<span class="number">0</span>) =&gt; <span class="number">0</span>  </span><br><span class="line"></span><br><span class="line"><span class="comment">//如果只传进来一个数据处理函数 就 直接执行</span></span><br><span class="line"><span class="keyword">let</span> operate = compose(add1)</span><br><span class="line">operate(<span class="number">0</span>) =&gt; <span class="number">0</span>  </span><br></pre></td></tr></table></figure>
<h2 id="函数的防抖"><a href="#函数的防抖" class="headerlink" title="函数的防抖"></a>函数的防抖</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 对于频繁触发的某个操作 我们只识别一次 </span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">handle</span>(<span class="params"></span>) </span>&#123;</span><br><span class="line">    <span class="built_in">setTimeout</span>(<span class="function">() =&gt;</span> &#123;</span><br><span class="line">        <span class="built_in">console</span>.log(<span class="string">&#x27;ok&#x27;</span>)</span><br><span class="line">    &#125;,<span class="number">1000</span>)</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">//如果我频繁点击submit这个按钮  他就会一直触发handle这个函数 一直输出OK  如果我们控制让它在300MS 无论你点几次 只触发一次</span></span><br><span class="line">submit.onclick = handle</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 在当前点击完成之后 我们等wait这么长的时间 看是否还会触发第二次 如果没有触发第二次 属于频繁操作 我们直接执行想要执行的函数func 如果触发了第二次 则以前的不算 从当前这次再开始等待</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// func 就是你要点击执行的那个函数 wait 就是我们控制在多少时间只内 只执行一次 inmmediate 就是我们让func这个函数 执行 你第一次触发 还是最后一次触发</span></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> * @params </span></span><br><span class="line"><span class="comment"> * func[function] 最后执行的函数</span></span><br><span class="line"><span class="comment"> * wait[number] 频繁设定的界限</span></span><br><span class="line"><span class="comment"> * inmmediate 默认多次操作 我们识别的是最后一次 但是inmmediate =true 让其识别第一次</span></span><br><span class="line"><span class="comment"> * @return 可以被调用执行的函数 </span></span><br><span class="line"><span class="comment"> */</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">debounce</span> (<span class="params">func,wait = <span class="number">300</span>, inmmediate =<span class="literal">false</span></span>)</span>&#123;</span><br><span class="line">    <span class="comment">//为什么return 因我们 submit.onclick = function (e) &#123;&#125; 也是执行一个匿名函数</span></span><br><span class="line">    <span class="comment">// 这里 我们可能还有事件对象 e 还有 事件源 this 也需要改变一下指向</span></span><br><span class="line">    <span class="keyword">let</span> timer = <span class="literal">null</span> <span class="comment">//主要是为了清除定时器用</span></span><br><span class="line">    <span class="keyword">return</span> <span class="function"><span class="keyword">function</span> <span class="title">anonymous</span>(<span class="params">...params</span>)</span>&#123;</span><br><span class="line">        <span class="comment">//我在第一次点击的时候 先清除一下定时器 因为第一没有 所以函数接着往下走</span></span><br><span class="line">        <span class="comment">//第二次的时候 我们清除了之后 定时器函数里面就不执行了 然后又重新开启了一个定时器 把上一次的取消了</span></span><br><span class="line">        <span class="built_in">clearTimeout</span>(timer)</span><br><span class="line">        timer = <span class="built_in">setTimeout</span>(<span class="function">() =&gt;</span> &#123;</span><br><span class="line">            <span class="comment">//执行你传进来的函数 并且把this的指向指向你的事件源 并且把事件对象传进去</span></span><br><span class="line">            func.call(<span class="built_in">this</span>,...params)</span><br><span class="line">        &#125;,wait)</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">// 以上 就触发 了最后一次 基本的防抖 就已经实现了</span></span><br><span class="line">submit.onclick = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">    </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 下面 我们要根据 inmmediate 来控制 只执行触发的第一次</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">debounce</span> (<span class="params">func,wait = <span class="number">300</span>, inmmediate =<span class="literal">false</span></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> timer = <span class="literal">null</span> </span><br><span class="line">    <span class="keyword">return</span> <span class="function"><span class="keyword">function</span> <span class="title">anonymous</span>(<span class="params">...params</span>)</span>&#123;</span><br><span class="line">        <span class="keyword">let</span> now = inmmediate  &amp;&amp;  !timer</span><br><span class="line">        <span class="built_in">clearTimeout</span>(timer)</span><br><span class="line">        <span class="comment">//我第一次进来 还是跟以前一样 设置一个定时器</span></span><br><span class="line">        timer = <span class="built_in">setTimeout</span>(<span class="function">() =&gt;</span> &#123;</span><br><span class="line">            <span class="comment">//3. 手动让定时器回归到初始状态</span></span><br><span class="line">            timer = <span class="literal">null</span></span><br><span class="line">          	<span class="comment">//2. 所以这里也要看看 如果是让我第一次执行 那我定时器里面的就都不执行了</span></span><br><span class="line">            !inmmediate?func.call(<span class="built_in">this</span>,...params) : <span class="literal">null</span></span><br><span class="line">        &#125;,wait)</span><br><span class="line">        <span class="comment">//1. 看看你是否让我立即执行 如果是 我就立即执行 但是同时你等了wait以后 定时器里面的也执行了</span></span><br><span class="line">        now?func.call(<span class="built_in">this</span>,...params):<span class="literal">null</span></span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">// 以上 就触发 了最后一次 基本的防抖 就已经实现了</span></span><br><span class="line">submit.onclick = <span class="function"><span class="keyword">function</span> (<span class="params"></span>) </span>&#123;</span><br><span class="line">    </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>
<h2 id="函数的节流"><a href="#函数的节流" class="headerlink" title="函数的节流"></a>函数的节流</h2><figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">1.</span> 让函数 在一定时间内 执行相应的次数</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">handle</span>(<span class="params"></span>)</span>&#123;</span><br><span class="line">    <span class="built_in">console</span>.log(<span class="string">&#x27;ok&#x27;</span>)</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">// 我们每一次的浏览器滚动过程中 都会触发上面那个函数 频率非常大 浏览器有最快反应时间(5~6ms 13-17ms) z只要反应过来了 就会触发函数</span></span><br><span class="line"><span class="built_in">window</span>.onscroll = handle</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="number">2.</span> 需要知道 我上一次触发的时间 到我这次的时间 小于我的频率时间 如果小于就不执行函数</span><br></pre></td></tr></table></figure>
<figure class="highlight js"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 每300ms触发一次</span></span><br><span class="line"><span class="comment">/*</span></span><br><span class="line"><span class="comment"> * @params</span></span><br><span class="line"><span class="comment"> * func[function]: 最后要触发执行的函数</span></span><br><span class="line"><span class="comment"> * wait[number]: 触发的频率</span></span><br><span class="line"><span class="comment"> * @return 可以被调用的执行函数</span></span><br><span class="line"><span class="comment">*/</span></span><br><span class="line"><span class="function"><span class="keyword">function</span> <span class="title">throttle</span> (<span class="params">func,wait = <span class="number">300</span></span>)</span>&#123;</span><br><span class="line">    <span class="keyword">let</span> timer = <span class="literal">null</span></span><br><span class="line">        previous = <span class="number">0</span>   <span class="comment">//记录上一次操作的时间</span></span><br><span class="line">    <span class="keyword">return</span> <span class="function"><span class="keyword">function</span> <span class="title">anonymous</span>(<span class="params">...params</span>)</span>&#123;</span><br><span class="line">        <span class="keyword">let</span> now = <span class="keyword">new</span> <span class="built_in">Date</span>() <span class="comment">//记录当前函数执行的时间</span></span><br><span class="line">            remaining = wait - (now - previous) <span class="comment">//记录还差多就达到我们一次触发的频率</span></span><br><span class="line">    	<span class="keyword">if</span>(remaining &lt;= <span class="number">0</span>)&#123;</span><br><span class="line">            <span class="built_in">clearTimeout</span>(timer)</span><br><span class="line">            timer = <span class="literal">null</span></span><br><span class="line">            <span class="comment">//等于我们的上一次触发时间</span></span><br><span class="line">            previous = now</span><br><span class="line">            <span class="comment">//如果这个小于0 就说明我们已经过了间隔时间 可以触发第二次了</span></span><br><span class="line">            func.call(<span class="built_in">this</span>,...params)</span><br><span class="line">        &#125;<span class="keyword">else</span> <span class="keyword">if</span>(!timer)&#123;</span><br><span class="line">            <span class="comment">// 如果你第二次点击发现没有设置定时器我才设置 如果设置了我就不设置了 因为你第二次进来的时候发现我等的那个函数还没执行 所以我就不用设置定时器 只有你没有 我才设置</span></span><br><span class="line">            <span class="comment">// 这里就说明 我们还在我们频率时间内点击了第二次 所以不能触发 我们要等</span></span><br><span class="line">        	timer = setTimerout(<span class="function">() =&gt;</span> &#123;</span><br><span class="line">                timer = <span class="literal">null</span></span><br><span class="line">                previous = <span class="keyword">new</span> <span class="built_in">Date</span>()</span><br><span class="line">                func.call(<span class="built_in">this</span>,...params)</span><br><span class="line">            &#125;,remaining)</span><br><span class="line">        &#125;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br><span class="line"></span><br><span class="line"><span class="built_in">window</span>.onscroll = throttle(handle)</span><br></pre></td></tr></table></figure>
</article><div class="post-copyright"><div class="post-copyright__title"><span class="post-copyright-info"><h>数据类型函数</h></span></div><div class="post-copyright__type"><span class="post-copyright-info"><a href="http://example.com/2019/03/31/%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E5%87%BD%E6%95%B0/">http://example.com/2019/03/31/%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E5%87%BD%E6%95%B0/</a></span></div><div class="post-copyright-m"><div class="post-copyright-m-info"><div class="post-copyright-a"><h>作者</h><div class="post-copyright-cc-info"><h>北城韩雨</h></div></div><div class="post-copyright-c"><h>发布于</h><div class="post-copyright-cc-info"><h>2019-03-31</h></div></div><div class="post-copyright-u"><h>更新于</h><div class="post-copyright-cc-info"><h>2019-06-03</h></div></div><div class="post-copyright-c"><h>许可协议</h><div class="post-copyright-cc-info"><a class="icon" rel="noopener" target="_blank" title="Creative Commons" href="https://creativecommons.org/"><i class="fab fa-creative-commons"></i></a><a rel="noopener" target="_blank" title="CC BY-NC-SA 4.0" href="https://creativecommons.org/licenses/by-nc-sa/4.0/">CC BY-NC-SA 4.0</a></div></div></div></div></div><div class="tag_share"><div class="post-meta__tag-list"><a class="post-meta__tags" href="/tags/JavaScript/">JavaScript</a></div><div class="post_share"></div></div><link rel="stylesheet" href="/" media="defer" onload="this.media='all'"/><div class="post-reward"><button class="tip-button reward-button"><span class="tip-button__text">打赏</span><div class="coin-wrapper"><div class="coin"><div class="coin__middle"></div><div class="coin__back"></div><div class="coin__front"></div></div></div><div class="reward-main"><ul class="reward-all"><li class="reward-item"><a href="/img/weixin.jpg" target="_blank"><img class="post-qr-code-img" src="/img/weixin.jpg" alt="微信"/></a><div class="post-qr-code-desc">微信</div></li><li class="reward-item"><a href="/img/taobao.jpg" target="_blank"><img class="post-qr-code-img" src="/img/taobao.jpg" alt="支付宝"/></a><div class="post-qr-code-desc">支付宝</div></li></ul></div></button></div><script defer="defer" src="/"></script><nav class="pagination-post" id="pagination"><div class="prev-post pull-left"><a href="/2019/03/31/jQuery%E8%A7%A3%E6%9E%90/"><img class="prev-cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2F3eca5394963b50e37b7be2ba320029ec%2F00003.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&amp;refer=http%3A%2F%2Fpic.vjshi.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530644&amp;t=10679b5732c52e39eeb588040240a790" onerror="onerror=null;src='/img/404.jpg'" alt="cover of previous post"><div class="pagination-info"><div class="label">上一篇</div><div class="prev_info">jQuery解析</div></div></a></div><div class="next-post pull-right"><a href="/2019/03/30/Promise/"><img class="next-cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2Faf41dabad727ba80c9ca8a2bfbd22a58%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&amp;refer=http%3A%2F%2Fpic.vjshi.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530659&amp;t=bbcfe1e86f393eecbb0722db1b92e475" onerror="onerror=null;src='/img/404.jpg'" alt="cover of next post"><div class="pagination-info"><div class="label">下一篇</div><div class="next_info">Promise</div></div></a></div></nav><div class="relatedPosts"><div class="headline"><i class="fas fa-thumbs-up fa-fw"></i><span> 相关推荐</span></div><div class="relatedPosts-list"><div><a href="/2020/04/27/写一个简版的Promise/" title="手写一个简版的promise"><img class="cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2017-07-20%2F4f06f9aa2ebcea6691a78537052e8e9f%2F00001.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&refer=http%3A%2F%2Fpic.vjshi.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530599&t=32fb97bad7007bdc6c712ccadacd5721" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2020-04-27</div><div class="title">手写一个简版的promise</div></div></a></div><div><a href="/2020/04/27/设计模式/" title="发布订阅"><img class="cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fcz-video-photo.oss-cn-beijing.aliyuncs.com%2F20191017%2F4cfc341591d242327b67e9ceb6953612_00002.jpg&refer=http%3A%2F%2Fcz-video-photo.oss-cn-beijing.aliyuncs.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530702&t=80943e12d5239f63beafd6d1c540855f" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2020-04-27</div><div class="title">发布订阅</div></div></a></div><div><a href="/2020/04/26/js事件循环机制/" title="JavaScript 事件循环机制"><img class="cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2F3eca5394963b50e37b7be2ba320029ec%2F00003.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&refer=http%3A%2F%2Fpic.vjshi.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530644&t=10679b5732c52e39eeb588040240a790" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2020-04-26</div><div class="title">JavaScript 事件循环机制</div></div></a></div><div><a href="/2020/04/22/ES6/" title="ES6/ES7/ES8/ES9/ES10/ES11"><img class="cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2Faf41dabad727ba80c9ca8a2bfbd22a58%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&refer=http%3A%2F%2Fpic.vjshi.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530659&t=bbcfe1e86f393eecbb0722db1b92e475" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2020-04-22</div><div class="title">ES6/ES7/ES8/ES9/ES10/ES11</div></div></a></div><div><a href="/2020/04/01/事件绑定/" title="事件绑定"><img class="cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2Faf41dabad727ba80c9ca8a2bfbd22a58%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&refer=http%3A%2F%2Fpic.vjshi.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530659&t=bbcfe1e86f393eecbb0722db1b92e475" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2020-04-01</div><div class="title">事件绑定</div></div></a></div><div><a href="/2020/03/29/Dialog/" title="弹框组件"><img class="cover" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fcz-video-photo.oss-cn-beijing.aliyuncs.com%2F20191017%2F4cfc341591d242327b67e9ceb6953612_00002.jpg&refer=http%3A%2F%2Fcz-video-photo.oss-cn-beijing.aliyuncs.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=jpeg?sec=1629530702&t=80943e12d5239f63beafd6d1c540855f" alt="cover"><div class="content is-center"><div class="date"><i class="far fa-calendar-alt fa-fw"></i> 2020-03-29</div><div class="title">弹框组件</div></div></a></div></div></div></div><div class="aside-content" id="aside-content"><div class="card-widget card-info"><div class="is-center"><div class="avatar-img"><img src="/img/my.jpg" onerror="this.onerror=null;this.src='/img/friend_404.gif'" alt="avatar"/></div><div class="author-info__name">北城韩雨</div><div class="author-info__description">一个前端界的小学生</div></div><div class="card-info-data"><div class="card-info-data-item is-center"><a href="/archives/"><div class="headline">文章</div><div class="length-num">65</div></a></div><div class="card-info-data-item is-center"><a href="/tags/"><div class="headline">标签</div><div class="length-num">23</div></a></div><div class="card-info-data-item is-center"><a href="/categories/"><div class="headline">分类</div><div class="length-num">21</div></a></div></div><a class="button--animated" id="card-info-btn" target="_blank" rel="noopener" href="https://github.com/wazer1987"><i class="fab fa-github"></i><span>Follow Me</span></a><div class="card-info-social-icons is-center"><a class="social-icon" href="/wangzhengvslike@163.com" target="_blank" title="Email"><i class="fas fa-envelope"></i></a></div></div><div class="card-widget card-announcement"><div class="item-headline"><i class="fas fa-bullhorn card-announcement-animation"></i><span>公告</span></div><div class="announcement_content"><p>感谢访问本站，如喜欢请收藏。本站主要分享前端知识，立志成为资深前端工程师，但目前是一个前端界的小学生 若喜欢可以打赏请博主喝一杯冰阔落</p> <p>另外请大家多多支持淼哥的开源项目</p> <p>https://github.com/flipped-aurora/gin-vue-admin</p> <p>🌟🌟欢迎大家start 🌟🌟</p> <p>欢迎加入博主的前端技术交流群</p> <p style="background:rgba(255,255,255,1);margin:0"> <img src="/img/code.png"></img> </p></div></div><div class="sticky_layout"><div class="card-widget" id="card-toc"><div class="item-headline"><i class="fas fa-stream"></i><span>目录</span></div><div class="toc-content"><ol class="toc"><li class="toc-item toc-level-2"><a class="toc-link" href="#%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B"><span class="toc-text">数据类型</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%9F%BA%E6%9C%AC%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B-%E5%8E%9F%E5%A7%8B%E5%80%BC%E7%B1%BB%E5%9E%8B"><span class="toc-text">基本数据类型(原始值类型)</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BC%95%E7%94%A8%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B-%E5%A4%8D%E6%9D%82%E7%B1%BB%E5%9E%8B"><span class="toc-text">引用数据类型(复杂类型)</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E4%BB%A3%E7%A0%81%E7%9A%84%E8%BF%90%E8%A1%8C"><span class="toc-text">代码的运行</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%9F%BA%E6%9C%AC%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B"><span class="toc-text">基本数据类型</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%A4%8D%E6%9D%82%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B"><span class="toc-text">复杂数据类型</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%B0%8F%E7%9F%A5%E8%AF%86%E7%82%B9"><span class="toc-text">小知识点</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%85%A8%E5%B1%80%E5%AF%B9%E8%B1%A1"><span class="toc-text">全局对象</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%A3%B0%E6%98%8E%E5%8F%98%E9%87%8F%E9%83%BD%E5%81%9A%E4%BA%86%E4%BB%80%E4%B9%88"><span class="toc-text">声明变量都做了什么</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%87%BD%E6%95%B0%E7%9A%84%E5%BA%95%E5%B1%82%E8%BF%90%E8%A1%8C%E6%9C%BA%E5%88%B6"><span class="toc-text">函数的底层运行机制</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%88%9B%E5%BB%BA%E5%87%BD%E6%95%B0"><span class="toc-text">创建函数</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%89%A7%E8%A1%8C%E5%87%BD%E6%95%B0"><span class="toc-text">执行函数</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E8%BD%AC%E6%8D%A2%E8%A7%84%E5%88%99"><span class="toc-text">数据类型转换规则</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%8A%8A%E5%85%B6%E4%BB%96%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E8%BD%AC%E6%8D%A2%E4%B8%BAnumber"><span class="toc-text">把其他数据类型转换为number</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%8A%8A%E5%85%B6%E4%BB%96%E6%95%B0%E6%8D%AE%E7%B1%BB%E5%9E%8B%E8%BD%AC%E6%8D%A2%E4%B8%BA%E5%AD%97%E7%AC%A6%E4%B8%B2"><span class="toc-text">把其他数据类型转换为字符串</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%8A%8A%E5%85%B6%E4%BB%96%E6%95%B0%E6%8D%AE%E8%BD%AC%E6%8D%A2%E4%B8%BA%E5%B8%83%E5%B0%94"><span class="toc-text">把其他数据转换为布尔</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%9C%A8-%E6%AF%94%E8%BE%83%E8%BF%87%E7%A8%8B%E4%B8%AD-%E6%95%B0%E6%8D%AE%E8%BD%AC%E6%8D%A2%E7%9A%84%E8%A7%84%E5%88%99"><span class="toc-text">在&#x3D;&#x3D;比较过程中 数据转换的规则</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%AF%B9%E8%B1%A1%E8%BD%AC%E6%8D%A2%E4%B8%BA%E5%AD%97%E7%AC%A6%E4%B8%B2"><span class="toc-text">对象转换为字符串</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E6%8A%8A%E5%85%B6%E4%BB%96%E7%B1%BB%E5%9E%8B%E8%BD%AC%E6%8D%A2%E4%B8%BA%E6%95%B0%E5%AD%97"><span class="toc-text">把其他类型转换为数字</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#parseInt%E6%9C%BA%E5%88%B6"><span class="toc-text">parseInt机制</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%B0%8F%E7%9F%A5%E8%AF%86"><span class="toc-text">小知识</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%8F%98%E9%87%8F%E5%A3%B0%E6%98%8E"><span class="toc-text">变量声明</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%8F%98%E9%87%8F%E6%8F%90%E5%8D%87%E6%9C%BA%E5%88%B6"><span class="toc-text">变量提升机制</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%9D%97%E7%BA%A7%E4%BD%9C%E7%94%A8%E5%9F%9F%E7%9A%84%E5%8F%98%E9%87%8F%E6%8F%90%E5%8D%87%E6%9C%BA%E5%88%B6"><span class="toc-text">块级作用域的变量提升机制</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E5%BD%A2%E5%8F%82%E9%BB%98%E8%AE%A4%E5%80%BC"><span class="toc-text">形参默认值</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E9%97%AD%E5%8C%85%E4%BD%9C%E7%94%A8%E5%9F%9F%E5%92%8C%E9%AB%98%E7%BA%A7%E7%BC%96%E7%A8%8B%E6%8A%80%E5%B7%A7"><span class="toc-text">闭包作用域和高级编程技巧</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#let-%E7%9A%84-for-%E5%BE%AA%E7%8E%AF%E6%9C%BA%E5%88%B6"><span class="toc-text">let 的 for 循环机制</span></a></li><li class="toc-item toc-level-3"><a class="toc-link" href="#%E4%BA%8B%E4%BB%B6%E7%BB%91%E5%AE%9A%E8%A7%A3%E5%86%B3%E6%96%B9%E6%A1%88"><span class="toc-text">事件绑定解决方案</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E7%9F%AD%E8%B7%AF%E8%AF%AD%E5%8F%A5"><span class="toc-text">短路语句</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#This"><span class="toc-text">This</span></a><ol class="toc-child"><li class="toc-item toc-level-3"><a class="toc-link" href="#this-%E7%9A%84%E6%89%A7%E8%A1%8C%E8%A7%84%E5%BE%8B"><span class="toc-text">this 的执行规律</span></a></li></ol></li><li class="toc-item toc-level-2"><a class="toc-link" href="#arguments-%E5%BD%A2%E5%8F%82%E6%98%A0%E5%B0%84%E6%9C%BA%E5%88%B6"><span class="toc-text">arguments 形参映射机制</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E6%A8%A1%E5%9D%97%E5%8C%96-%E5%8D%95%E5%88%97%E6%A8%A1%E5%BC%8F%E8%AE%BE%E8%AE%A1%E6%A8%A1%E5%BC%8F"><span class="toc-text">模块化 &#x2F; 单列模式设计模式</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E6%83%B0%E6%80%A7%E5%87%BD%E6%95%B0"><span class="toc-text">惰性函数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E6%9F%AF%E9%87%8C%E5%8C%96%E5%87%BD%E6%95%B0"><span class="toc-text">柯里化函数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E7%BB%84%E5%90%88%E5%87%BD%E6%95%B0"><span class="toc-text">组合函数</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%87%BD%E6%95%B0%E7%9A%84%E9%98%B2%E6%8A%96"><span class="toc-text">函数的防抖</span></a></li><li class="toc-item toc-level-2"><a class="toc-link" href="#%E5%87%BD%E6%95%B0%E7%9A%84%E8%8A%82%E6%B5%81"><span class="toc-text">函数的节流</span></a></li></ol></div></div><div class="card-widget card-recent-post"><div class="item-headline"><i class="fas fa-history"></i><span>最新文章</span></div><div class="aside-list"><div class="aside-list-item"><a class="thumbnail" href="/2021/04/16/gin-vue-admin/" title="Gin-Vue-Admin"><img src="/img/gin-vue-admin.jpg" onerror="this.onerror=null;this.src='/img/404.jpg'" alt="Gin-Vue-Admin"/></a><div class="content"><a class="title" href="/2021/04/16/gin-vue-admin/" title="Gin-Vue-Admin">Gin-Vue-Admin</a><time datetime="2021-04-15T16:00:00.000Z" title="发表于 2021-04-16 00:00:00">2021-04-16</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/2021/01/08/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E7%BB%84%E4%BB%B6%E7%9A%84%E6%B8%B2%E6%9F%9310/" title="Vue源码开发-组件的渲染10"><img src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2F3eca5394963b50e37b7be2ba320029ec%2F00003.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&amp;refer=http%3A%2F%2Fpic.vjshi.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530644&amp;t=10679b5732c52e39eeb588040240a790" onerror="this.onerror=null;this.src='/img/404.jpg'" alt="Vue源码开发-组件的渲染10"/></a><div class="content"><a class="title" href="/2021/01/08/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E7%BB%84%E4%BB%B6%E7%9A%84%E6%B8%B2%E6%9F%9310/" title="Vue源码开发-组件的渲染10">Vue源码开发-组件的渲染10</a><time datetime="2021-01-07T16:00:00.000Z" title="发表于 2021-01-08 00:00:00">2021-01-08</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/2021/01/07/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E7%BB%84%E4%BB%B6%E7%9A%84%E5%90%88%E5%B9%B6%E7%AD%96%E7%95%A509/" title="Vue源码开发-组件合并策略09"><img src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fcz-video-photo.oss-cn-beijing.aliyuncs.com%2F20191017%2F4cfc341591d242327b67e9ceb6953612_00002.jpg&amp;refer=http%3A%2F%2Fcz-video-photo.oss-cn-beijing.aliyuncs.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530702&amp;t=80943e12d5239f63beafd6d1c540855f" onerror="this.onerror=null;this.src='/img/404.jpg'" alt="Vue源码开发-组件合并策略09"/></a><div class="content"><a class="title" href="/2021/01/07/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E7%BB%84%E4%BB%B6%E7%9A%84%E5%90%88%E5%B9%B6%E7%AD%96%E7%95%A509/" title="Vue源码开发-组件合并策略09">Vue源码开发-组件合并策略09</a><time datetime="2021-01-06T16:00:00.000Z" title="发表于 2021-01-07 00:00:00">2021-01-07</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/2021/01/06/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E6%95%B0%E7%BB%84%E7%9A%84%E4%BE%9D%E8%B5%96%E6%94%B6%E9%9B%8608/" title="Vue源码开发-数组的依赖收集08"><img src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2F3eca5394963b50e37b7be2ba320029ec%2F00003.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&amp;refer=http%3A%2F%2Fpic.vjshi.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530644&amp;t=10679b5732c52e39eeb588040240a790" onerror="this.onerror=null;this.src='/img/404.jpg'" alt="Vue源码开发-数组的依赖收集08"/></a><div class="content"><a class="title" href="/2021/01/06/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E6%95%B0%E7%BB%84%E7%9A%84%E4%BE%9D%E8%B5%96%E6%94%B6%E9%9B%8608/" title="Vue源码开发-数组的依赖收集08">Vue源码开发-数组的依赖收集08</a><time datetime="2021-01-05T16:00:00.000Z" title="发表于 2021-01-06 00:00:00">2021-01-06</time></div></div><div class="aside-list-item"><a class="thumbnail" href="/2021/01/06/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E5%90%88%E5%B9%B607/" title="Vue源码开发-生命周期合并07"><img src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fpic.vjshi.com%2F2018-07-17%2Faf41dabad727ba80c9ca8a2bfbd22a58%2F00004.jpg%3Fx-oss-process%3Dstyle%2Fwatermark&amp;refer=http%3A%2F%2Fpic.vjshi.com&amp;app=2002&amp;size=f9999,10000&amp;q=a80&amp;n=0&amp;g=0n&amp;fmt=jpeg?sec=1629530659&amp;t=bbcfe1e86f393eecbb0722db1b92e475" onerror="this.onerror=null;this.src='/img/404.jpg'" alt="Vue源码开发-生命周期合并07"/></a><div class="content"><a class="title" href="/2021/01/06/Vue%E6%BA%90%E7%A0%81%E5%BC%80%E5%8F%91%E4%B9%8B%E7%94%9F%E5%91%BD%E5%91%A8%E6%9C%9F%E5%90%88%E5%B9%B607/" title="Vue源码开发-生命周期合并07">Vue源码开发-生命周期合并07</a><time datetime="2021-01-05T16:00:00.000Z" title="发表于 2021-01-06 00:00:00">2021-01-06</time></div></div></div></div></div></div></main><footer id="footer"><div id="footer-wrap"><div class="copyright"><span>&copy;2017 - 2021</span><svg style="width:2em; height:2em;position: relative;top: 10px;" aria-hidden="true"><use xlink:href="#icon-Butterfly"></use></svg><span>北城韩雨</span></div><div class="framework-info"><span>框架 </span><a target="_blank" rel="noopener" href="https://hexo.io">Hexo</a><span class="footer-separator">|</span><span>主题 </span><a target="_blank" rel="noopener" href="https://github.com/jerryc127/hexo-theme-butterfly">Butterfly</a></div><div class="footer_custom_text"><p><a style="margin-inline:5px" target="_blank" href="https://hexo.io/"><img src="https://img.shields.io/badge/Frame-Hexo-blue?style=flat&logo=hexo" title="博客框架为Hexo"></a><a style="margin-inline:5px" target="_blank" href="https://butterfly.js.org/"><img src="https://img.shields.io/badge/Theme-Butterfly-6513df?style=flat&logo=bitdefender" title="主题采用butterfly"></a><a style="margin-inline:5px" target="_blank" href="https://www.jsdelivr.com/"><img src="https://img.shields.io/badge/CDN-jsDelivr-orange?style=flat&logo=jsDelivr" title="本站使用JsDelivr为静态资源提供CDN加速"></a></p></div></div></footer></div><div id="rightside"><div id="rightside-config-hide"><button id="readmode" type="button" title="阅读模式"><i class="fas fa-book-open"></i></button><button id="darkmode" type="button" title="浅色和深色模式转换"><i class="fas fa-adjust"></i></button></div><div id="rightside-config-show"><button id="rightside_config" type="button" title="设置"><i class="fas fa-cog fa-spin"></i></button><button class="close" id="mobile-toc-button" type="button" title="目录"><i class="fas fa-list-ul"></i></button><button id="go-up" type="button" title="回到顶部"><i class="fas fa-arrow-up"></i></button></div></div><div><script src="/js/utils.js"></script><script src="/js/main.js"></script><script src="https://cdn.jsdelivr.net/npm/medium-zoom/dist/medium-zoom.min.js"></script><div class="js-pjax"></div><script defer src="/live2d-widget/autoload.js"></script><script src="/js/coin.js"></script><script async src="//at.alicdn.com/t/font_2700632_3rtvhzzpl3h.js"></script><script src="/js/liuxing.js" data-pjax></script><canvas class="fireworks" mobile="false"></canvas><script src="https://cdn.jsdelivr.net/npm/butterfly-extsrc@1/dist/fireworks.min.js"></script><script src="https://cdn.jsdelivr.net/npm/butterfly-extsrc@1/dist/activate-power-mode.min.js"></script><script>POWERMODE.colorful = true;
POWERMODE.shake = true;
POWERMODE.mobile = false;
document.body.addEventListener('input', POWERMODE);
</script><script async data-pjax src="//busuanzi.ibruce.info/busuanzi/2.3/busuanzi.pure.mini.js"></script></div><!-- hexo injector body_end start --><div class="js-pjax"><script async="async">var arr = document.getElementsByClassName('recent-post-item');
for(var i = 0;i<arr.length;i++){
    arr[i].classList.add('wow');
    arr[i].classList.add('animate__zoomIn');
    arr[i].setAttribute('data-wow-duration', '1s');
    arr[i].setAttribute('data-wow-delay', '0ms');
    arr[i].setAttribute('data-wow-offset', '100');
    arr[i].setAttribute('data-wow-iteration', '1');
  }</script><script async="async">var arr = document.getElementsByClassName('card-widget');
for(var i = 0;i<arr.length;i++){
    arr[i].classList.add('wow');
    arr[i].classList.add('animate__zoomIn');
    arr[i].setAttribute('data-wow-duration', '');
    arr[i].setAttribute('data-wow-delay', '');
    arr[i].setAttribute('data-wow-offset', '');
    arr[i].setAttribute('data-wow-iteration', '');
  }</script></div><script defer src="https://cdn.jsdelivr.net/gh/graingert/wow@1.3.0/dist/wow.min.js"></script><script defer src="https://cdn.jsdelivr.net/npm/hexo-butterfly-wowjs/lib/wow_init.min.js"></script><script async src="//at.alicdn.com/t/font_2032782_8d5kxvn09md.js"></script><!-- hexo injector body_end end --></body></html>